Make WordPress Core

Changeset 31410 for branches/4.1


Ignore:
Timestamp:
02/11/2015 06:24:01 AM (10 years ago)
Author:
dd32
Message:

Ensure that WP_Customize_Setting::value() returns default value for setting if not dirty.

There was regression introduced by #28580 where only changed (dirty) settings now are POST'ed to the Customizer preview.

  • Allow WP_Customize_Manager::post_value() to accept a second $default argument.
  • Introduce WP_Customize_Manager::unsanitized_post_values() for accessing previously-private member variable _post_values.
  • Do require_once instead of require for Customizer classes.
  • Add unit tests for WP_Customize_Manager and WP_Customize_Setting.

Props westonruter, boonebgorges.
Merges [31329] [31339] [31342] [31360] to the 4.1 branch.
Fixes #30988.

Location:
branches/4.1
Files:
4 edited
1 copied

Legend:

Unmodified
Added
Removed
  • branches/4.1

  • branches/4.1/src/wp-includes/class-wp-customize-manager.php

    r30931 r31410  
    6464
    6565    /**
    66      * $_POST values for Customize Settings.
    67      *
    68      * @var array
     66     * Unsanitized values for Customize Settings parsed from $_POST['customized'].
     67     *
     68     * @var array|false
    6969     */
    7070    private $_post_values;
     
    7676     */
    7777    public function __construct() {
    78         require( ABSPATH . WPINC . '/class-wp-customize-setting.php' );
    79         require( ABSPATH . WPINC . '/class-wp-customize-panel.php' );
    80         require( ABSPATH . WPINC . '/class-wp-customize-section.php' );
    81         require( ABSPATH . WPINC . '/class-wp-customize-control.php' );
    82         require( ABSPATH . WPINC . '/class-wp-customize-widgets.php' );
     78        require_once( ABSPATH . WPINC . '/class-wp-customize-setting.php' );
     79        require_once( ABSPATH . WPINC . '/class-wp-customize-panel.php' );
     80        require_once( ABSPATH . WPINC . '/class-wp-customize-section.php' );
     81        require_once( ABSPATH . WPINC . '/class-wp-customize-control.php' );
     82        require_once( ABSPATH . WPINC . '/class-wp-customize-widgets.php' );
    8383
    8484        $this->widgets = new WP_Customize_Widgets( $this );
     
    400400
    401401    /**
    402      * Decode the $_POST['customized'] values for a specific Customize Setting.
    403      *
    404      * @since 3.4.0
     402     * Parse the incoming $_POST['customized'] JSON data and store the unsanitized
     403     * settings for subsequent post_value() lookups.
     404     *
     405     * @since 4.1.1
     406     *
     407     * @return array
     408     */
     409    public function unsanitized_post_values() {
     410        if ( ! isset( $this->_post_values ) ) {
     411            if ( isset( $_POST['customized'] ) ) {
     412                $this->_post_values = json_decode( wp_unslash( $_POST['customized'] ), true );
     413            }
     414            if ( empty( $this->_post_values ) ) { // if not isset or of JSON error
     415                $this->_post_values = false;
     416            }
     417        }
     418        if ( empty( $this->_post_values ) ) {
     419            return array();
     420        } else {
     421            return $this->_post_values;
     422        }
     423    }
     424
     425    /**
     426     * Return the sanitized value for a given setting from the request's POST data.
     427     *
     428     * @since 3.4.0
     429     * @since 4.1.1 Introduced 'default' parameter.
    405430     *
    406431     * @param WP_Customize_Setting $setting A WP_Customize_Setting derived object
    407      * @return string $post_value Sanitized value
    408      */
    409     public function post_value( $setting ) {
    410         if ( ! isset( $this->_post_values ) ) {
    411             if ( isset( $_POST['customized'] ) )
    412                 $this->_post_values = json_decode( wp_unslash( $_POST['customized'] ), true );
    413             else
    414                 $this->_post_values = false;
    415         }
    416 
    417         if ( isset( $this->_post_values[ $setting->id ] ) )
    418             return $setting->sanitize( $this->_post_values[ $setting->id ] );
     432     * @param mixed $default value returned $setting has no post value (added in 4.2.0).
     433     * @return string|mixed $post_value Sanitized value or the $default provided
     434     */
     435    public function post_value( $setting, $default = null ) {
     436        $post_values = $this->unsanitized_post_values();
     437        if ( array_key_exists( $setting->id, $post_values ) ) {
     438            return $setting->sanitize( $post_values[ $setting->id ] );
     439        } else {
     440            return $default;
     441        }
    419442    }
    420443
  • branches/4.1/src/wp-includes/class-wp-customize-setting.php

    r30676 r31410  
    104104    }
    105105
     106    protected $_original_value;
     107
    106108    /**
    107109     * Handle previewing the setting.
     
    110112     */
    111113    public function preview() {
     114        if ( ! isset( $this->_original_value ) ) {
     115            $this->_original_value = $this->value();
     116        }
     117
    112118        switch( $this->type ) {
    113119            case 'theme_mod' :
     
    160166     */
    161167    public function _preview_filter( $original ) {
    162         return $this->multidimensional_replace( $original, $this->id_data[ 'keys' ], $this->post_value() );
     168        $undefined = new stdClass(); // symbol hack
     169        $post_value = $this->manager->post_value( $this, $undefined );
     170        if ( $undefined === $post_value ) {
     171            $value = $this->_original_value;
     172        } else {
     173            $value = $post_value;
     174        }
     175
     176        return $this->multidimensional_replace( $original, $this->id_data['keys'], $value );
    163177    }
    164178
     
    426440        }
    427441
    428         if ( $create && ! isset( $node[ $last ] ) )
    429             $node[ $last ] = array();
     442        if ( $create ) {
     443            if ( ! is_array( $node ) ) {
     444                // account for an array overriding a string or object value
     445                $node = array();
     446            }
     447            if ( ! isset( $node[ $last ] ) ) {
     448                $node[ $last ] = array();
     449            }
     450        }
    430451
    431452        if ( ! isset( $node[ $last ] ) )
  • branches/4.1/tests/phpunit/tests/customize/setting.php

    r31329 r31410  
    216216            $this->arrayHasKey( 'bar', $base_value );
    217217            $this->assertEquals( $base_initial_value['foo'], $base_value['foo'] );
    218             $this->assertEquals( $base_initial_value['bar'], call_user_func( $type_options['getter'], $base_name, $this->undefined )['bar'] );
     218
     219            $getter = call_user_func( $type_options['getter'], $base_name, $this->undefined );
     220            $this->assertEquals( $base_initial_value['bar'], $getter['bar'] );
    219221            $this->assertEquals( $initial_value, $setting->value() );
    220222            $setting->preview();
     
    225227            $this->assertEquals( $this->post_data_overrides[ $name ], $base_value['foo'] );
    226228            $this->arrayHasKey( 'bar', call_user_func( $type_options['getter'], $base_name, $this->undefined ) );
    227             $this->assertEquals( $base_initial_value['bar'], call_user_func( $type_options['getter'], $base_name, $this->undefined )['bar'] );
     229
     230            $getter = call_user_func( $type_options['getter'], $base_name, $this->undefined );
     231            $this->assertEquals( $base_initial_value['bar'], $getter['bar'] );
    228232        }
    229233    }
Note: See TracChangeset for help on using the changeset viewer.