Skip to:
Content

BuddyPress.org

Ticket #7226: 7226-07.patch

File 7226-07.patch, 8.8 KB (added by hnla, 3 years ago)

Correct various issues with escaping data.

  • src/bp-core/classes/class-bp-button.php

     
    3333 *                                          Default: ''.
    3434 *     @type string      $wrapper_class     Optional. DOM class of the button wrapper
    3535 *                                          element. Default: ''.
     36 *     @type string      $element           Optional. The type of element to use e.g 'anchor', 'button', 'input'
     37 *                                          Default: 'anchor'.
     38 *     @type string      $element_type      Optional. Set the button type i.e like input types
     39 *                                          Defaults to 'button' [type="button"] can be 'submit' [type="submit"]
     40 *     @type string      $name              Button/input 'name' value - if type == 'submit' || 'reset.
     41 *     @type string      $value             Button/input 'value' value - if type == 'submit' || 'reset'.
    3642 *     @type string      $link_href         Optional. Destination link of the button.
    3743 *                                          Default: ''.
     44 *     @type string      $data_attr         Optional. Allow data attributtes to be set. e.g 'data-bp-buttons=""'
     45 *                                          Takes an array of key/value pairs to allow for multiple attrs.
     46 *                                          Default: ''.
    3847 *     @type string      $link_class        Optional. DOM class of the button. Default: ''.
    3948 *     @type string      $link_id           Optional. DOM ID of the button. Default: ''.
    4049 *     @type string      $link_rel          Optional. DOM 'rel' attribute of the button.
     
    8291        /**
    8392         * The type of DOM element to use for a wrapper.
    8493         *
    85          * @var string|bool 'div', 'span', 'p', 'li', or false for no wrapper.
     94         * @var string|bool 'div', 'li',  'p', 'span' or false for no wrapper.
    8695         */
    8796        public $wrapper = 'div';
    8897
     
    103112        /** Button ****************************************************************/
    104113
    105114        /**
     115        * The node element type type i.e. a true '<button>', '<a>' or '<input />':
     116        * 'button', 'anchor', 'input'
     117        *
     118        * @var string
     119        */
     120        public $element = 'anchor';
     121
     122        /**
     123        * The button/input elements type i.e. 'submit', 'button', 'reset'.
     124        *
     125        *
     126        * @var string
     127        */
     128        public $element_type = 'button';
     129
     130        /**
     131        * The button/input elements name attr i.e. 'name=""'.
     132        *
     133        *
     134        * @var string
     135        */
     136        public $name = '';
     137
     138        /**
     139        * The button/input elements value attr i.e. 'value=""'.
     140        *
     141        *
     142        * @var string
     143        */
     144        public $value = '';
     145
     146
     147        /**
    106148         * The destination link of the button.
    107149         *
    108150         * @var string
     
    138180        public $link_title = '';
    139181
    140182        /**
     183         * Data attributes.
     184                * Takes an array of key/value pairs to loop over.
     185         *
     186         * @var array
     187         */
     188        public $data_attr = '';
     189
     190        /**
    141191         * The contents of the button link.
    142192         *
    143193         * @var string
     
    164214                $r = wp_parse_args( $args, get_class_vars( __CLASS__ ) );
    165215
    166216                // Required button properties.
    167                 $this->id                = $r['id'];
     217                $this->id                = esc_attr( $r['id'] );
    168218                $this->component         = $r['component'];
    169219                $this->must_be_logged_in = (bool) $r['must_be_logged_in'];
    170220                $this->block_self        = (bool) $r['block_self'];
    171                 $this->wrapper           = $r['wrapper'];
     221                $this->wrapper           = $r['wrapper'] ;
    172222
    173223                // $id and $component are required
    174224                if ( empty( $r['id'] ) || empty( $r['component'] ) )
     
    202252                // Wrapper properties.
    203253                if ( false !== $this->wrapper ) {
    204254
     255                /**
     256                        * Currently BP does not provide for a wrapping group element, templates
     257                        * would need to provide the  parent wrapper in the template if li
     258                        * specified as wrapper.
     259                        */
     260
    205261                        // Wrapper ID.
    206262                        if ( !empty( $r['wrapper_id'] ) ) {
    207                                 $this->wrapper_id    = ' id="' . $r['wrapper_id'] . '"';
     263                                $this->wrapper_id  = ' id="' . esc_attr( $r['wrapper_id'] ) . '"';
    208264                        }
    209265
    210266                        // Wrapper class.
    211                         if ( !empty( $r['wrapper_class'] ) ) {
    212                                 $this->wrapper_class = ' class="generic-button ' . $r['wrapper_class'] . '"';
    213                         } else {
    214                                 $this->wrapper_class = ' class="generic-button"';
     267                        if ( !empty( $r['wrapper_class'] )  ) {
     268                                $this->wrapper_class = ' class="generic-button ' . esc_attr( $r['wrapper_class'] ) . '"';
    215269                        }
    216270
    217271                        // Set before and after.
    218                         $before = '<' . $r['wrapper'] . $this->wrapper_class . $this->wrapper_id . '>';
    219                         $after  = '</' . $r['wrapper'] . '>';
     272                        // Include 'li' elements if wrapper = 'ul'
     273                        $before = '<'  . $this->wrapper . $this->wrapper_class . $this->wrapper_id . '>';
     274                        $after  = '</' . $this->wrapper . '>';
    220275
    221276                // No wrapper.
    222277                } else {
     
    223278                        $before = $after = '';
    224279                }
    225280
    226                 // Link properties.
    227                 if ( !empty( $r['link_id']    ) ) $this->link_id    = ' id="' .    $r['link_id']    . '"';
    228                 if ( !empty( $r['link_href']  ) ) $this->link_href  = ' href="' .  $r['link_href']  . '"';
    229                 if ( !empty( $r['link_title'] ) ) $this->link_title = ' title="' . $r['link_title'] . '"';
    230                 if ( !empty( $r['link_rel']   ) ) $this->link_rel   = ' rel="' .   $r['link_rel']   . '"';
    231                 if ( !empty( $r['link_class'] ) ) $this->link_class = ' class="' . $r['link_class'] . '"';
    232                 if ( !empty( $r['link_text']  ) ) $this->link_text  =              $r['link_text'];
     281                // Link/Button/input  attributes.
     282                //if ( !empty( $r['element']    ) ) $this->element    =
     283                if ( 'button' == $r['element'] || 'input' == $r['element'] ) {
     284                        if ( !empty( $r['element_type'] ) ) $this->element_type = ' type="' . esc_attr( $r['element_type'] ) . '"';
     285                        if( 'submit' == $r['element_type'] || 'reset' == $r['element_type'] ) {
     286                                if ( !empty( $r['name']  ) ) $this->name  = ' name="'  . esc_attr( $r['name'] )  . '"';
     287                                if ( !empty( $r['value'] ) ) $this->value = ' value="' . esc_attr( $r['value'] ) . '"';
     288                        }
     289                }
    233290
     291                if ( !empty( $r['link_id']    ) ) $this->link_id    = ' id="'    .   esc_attr( $r['link_id'] )   . '"';
     292                // No href if we're a button please!
     293                if ( !empty( $r['link_href']  ) ) $this->link_href  = ' href="'  .   esc_url(  $r['link_href'] )  . '"';
     294                if ( !empty( $r['link_title'] ) ) $this->link_title = ' title="' .   esc_attr( $r['link_title'] ) . '"';
     295                if ( !empty( $r['link_rel']   ) ) $this->link_rel   = ' rel="'   .   esc_attr( $r['link_rel'] )   . '"';
     296                if ( !empty( $r['link_class'] ) ) $this->link_class = ' class="' .   esc_attr( $r['link_class'] ) . '"';
     297                if ( !empty( $r['link_text']  ) && 'input' !== $r['element'] ) $this->link_text  = $r['link_text'] ;
     298
     299                /**
     300                * Build data attr to display
     301                * loop over $r['data_attr'] & build as many data-foo="bar" instances as array pairs found
     302                */
     303
     304                if ( !empty( $r['data_attr'] ) ) {
     305
     306                        $data_attr = $r['data_attr'];
     307                        foreach ($data_attr as $key => $value) {
     308                        $this->data_attr .= 'data-' . sanitize_key( $key ) . '="' . esc_attr( $value ) . '"';
     309                        }
     310
     311                } else {
     312                        $this->data_attr = '';
     313                }
     314
     315                // The wrapper element
     316
     317                // The element tag: e.g '<a', '<button'
     318
     319                if ( 'button' == $r['element'] || 'input' == $r['element'] ) {
     320
     321                        // If the element type is submit we'll build the button/input form controls attr here
     322                        if( 'submit' == $r['element_type'] ) {
     323                                $element_controls = $this->name . $this->value ;
     324                        } else {
     325                                $element_controls = '';
     326                        }
     327
     328                        if ( 'button' == $r['element'] ){
     329                                        $before_element = '<button ' . $this->element_type . $element_controls;
     330                                        $after_element  = '</button>';
     331                        } elseif( 'input' == $r['element'] ) {
     332                                        $before_element = '<input ' . $this->element_type . $element_controls;
     333                                        $after_element  = '';
     334                        }
     335
     336
     337                } else {
     338                        $before_element = '<a ' . $this->link_href;
     339                        $after_element  = '</a>';
     340                }
     341
    234342                // Build the button.
    235                 $this->contents = $before . '<a'. $this->link_href . $this->link_title . $this->link_id . $this->link_rel . $this->link_class . '>' . $this->link_text . '</a>' . $after;
     343                // attr here can be applicable/common to anchors or button elements
     344                $this->contents = $before . $before_element . $this->link_title . $this->link_id . $this->link_class . $this->link_rel . $this->data_attr . '>' . $this->link_text . $after_element . $after;
    236345
    237346                /**
    238347                 * Filters the button based on class parameters.
     
    246355                 * @param BP_Button $this     Current BP_Button instance.
    247356                 * @param string    $before   HTML appended before the actual button.
    248357                 * @param string    $after    HTML appended after the actual button.
     358                 * @param string    $before_element  Actual items opening element.
     359                 * @param string    $after_element   Actual items closing element  .
    249360                 */
    250                 $this->contents = apply_filters( 'bp_button_' . $this->component . '_' . $this->id, $this->contents, $this, $before, $after );
     361                $this->contents = apply_filters( 'bp_button_' . $this->component . '_' . $this->id, $this->contents, $this, $before, $after, $before_element, $after_element );
    251362        }
    252363
    253364        /**