Skip to content

Commit 9f1b37a

Browse files
always escape as if context is HTML, maybe escape as if context is attribute
1 parent f7eb022 commit 9f1b37a

File tree

5 files changed

+43
-39
lines changed

5 files changed

+43
-39
lines changed

includes/class-dynamic-content-tags.php

Lines changed: 38 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@ abstract class MC4WP_Dynamic_Content_Tags
1111
/**
1212
* @var string The escape function for replacement values.
1313
*/
14-
protected $escape_function = null;
14+
protected $escape_function = 'esc_html';
1515

1616
/**
1717
* @var array Array of registered dynamic content tags
@@ -25,56 +25,56 @@ protected function register()
2525
{
2626
// Global tags can go here
2727
$this->tags['cookie'] = [
28-
'description' => __('Data from a cookie.', 'mailchimp-for-wp'),
29-
'callback' => [ $this, 'get_cookie' ],
30-
'example' => "cookie name='my_cookie' default='Default Value'",
28+
'description' => __('Data from a cookie.', 'mailchimp-for-wp'),
29+
'callback' => [ $this, 'get_cookie' ],
30+
'example' => "cookie name='my_cookie' default='Default Value'",
3131
];
3232

3333
$this->tags['email'] = [
34-
'description' => __('The email address of the current visitor (if known).', 'mailchimp-for-wp'),
35-
'callback' => [ $this, 'get_email' ],
34+
'description' => __('The email address of the current visitor (if known).', 'mailchimp-for-wp'),
35+
'callback' => [ $this, 'get_email' ],
3636
];
3737

3838
$this->tags['current_url'] = [
39-
'description' => __('The URL of the page.', 'mailchimp-for-wp'),
40-
'callback' => 'mc4wp_get_request_url',
39+
'description' => __('The URL of the page.', 'mailchimp-for-wp'),
40+
'callback' => 'mc4wp_get_request_url',
4141
];
4242

4343
$this->tags['current_path'] = [
44-
'description' => __('The path of the page.', 'mailchimp-for-wp'),
45-
'callback' => 'mc4wp_get_request_path',
44+
'description' => __('The path of the page.', 'mailchimp-for-wp'),
45+
'callback' => 'mc4wp_get_request_path',
4646
];
4747

4848
$this->tags['date'] = [
49-
'description' => sprintf(__('The current date. Example: %s.', 'mailchimp-for-wp'), '<strong>' . gmdate('Y/m/d', time() + ( get_option('gmt_offset') * HOUR_IN_SECONDS )) . '</strong>'),
50-
'replacement' => gmdate('Y/m/d', time() + ( get_option('gmt_offset') * HOUR_IN_SECONDS )),
49+
'description' => sprintf(__('The current date. Example: %s.', 'mailchimp-for-wp'), '<strong>' . gmdate('Y/m/d', time() + ( get_option('gmt_offset') * HOUR_IN_SECONDS )) . '</strong>'),
50+
'replacement' => gmdate('Y/m/d', time() + ( get_option('gmt_offset') * HOUR_IN_SECONDS )),
5151
];
5252

5353
$this->tags['time'] = [
54-
'description' => sprintf(__('The current time. Example: %s.', 'mailchimp-for-wp'), '<strong>' . gmdate('H:i:s', time() + ( get_option('gmt_offset') * HOUR_IN_SECONDS )) . '</strong>'),
55-
'replacement' => gmdate('H:i:s', time() + ( get_option('gmt_offset') * HOUR_IN_SECONDS )),
54+
'description' => sprintf(__('The current time. Example: %s.', 'mailchimp-for-wp'), '<strong>' . gmdate('H:i:s', time() + ( get_option('gmt_offset') * HOUR_IN_SECONDS )) . '</strong>'),
55+
'replacement' => gmdate('H:i:s', time() + ( get_option('gmt_offset') * HOUR_IN_SECONDS )),
5656
];
5757

5858
$this->tags['language'] = [
59-
'description' => sprintf(__('The site\'s language. Example: %s.', 'mailchimp-for-wp'), '<strong>' . get_locale() . '</strong>'),
60-
'callback' => 'get_locale',
59+
'description' => sprintf(__('The site\'s language. Example: %s.', 'mailchimp-for-wp'), '<strong>' . get_locale() . '</strong>'),
60+
'callback' => 'get_locale',
6161
];
6262

6363
$this->tags['ip'] = [
64-
'description' => sprintf(__('The visitor\'s IP address. Example: %s.', 'mailchimp-for-wp'), '<strong>' . mc4wp_get_request_ip_address() . '</strong>'),
65-
'callback' => 'mc4wp_get_request_ip_address',
64+
'description' => sprintf(__('The visitor\'s IP address. Example: %s.', 'mailchimp-for-wp'), '<strong>' . mc4wp_get_request_ip_address() . '</strong>'),
65+
'callback' => 'mc4wp_get_request_ip_address',
6666
];
6767

6868
$this->tags['user'] = [
69-
'description' => __('The property of the currently logged-in user.', 'mailchimp-for-wp'),
70-
'callback' => [ $this, 'get_user_property' ],
71-
'example' => "user property='user_email'",
69+
'description' => __('The property of the currently logged-in user.', 'mailchimp-for-wp'),
70+
'callback' => [ $this, 'get_user_property' ],
71+
'example' => "user property='user_email'",
7272
];
7373

7474
$this->tags['post'] = [
75-
'description' => __('Property of the current page or post.', 'mailchimp-for-wp'),
76-
'callback' => [ $this, 'get_post_property' ],
77-
'example' => "post property='ID'",
75+
'description' => __('Property of the current page or post.', 'mailchimp-for-wp'),
76+
'callback' => [ $this, 'get_post_property' ],
77+
'example' => "post property='ID'",
7878
];
7979
}
8080

@@ -118,9 +118,8 @@ protected function replace_tag(array $matches)
118118
$replacement = call_user_func($config['callback'], $attributes);
119119
}
120120

121-
if (is_callable($this->escape_function)) {
122-
$replacement = call_user_func($this->escape_function, $replacement);
123-
}
121+
// escape replacement value
122+
$replacement = call_user_func($this->escape_function, $replacement);
124123

125124
return $replacement;
126125
}
@@ -131,15 +130,21 @@ protected function replace_tag(array $matches)
131130

132131
/**
133132
* @param string $string The string containing dynamic content tags.
134-
* @param string $escape_function Escape mode for the replacement value. Leave empty for no escaping.
133+
* @param string $escape_function Escape mode for the replacement value.
135134
* @return string
136135
*/
137-
protected function replace($string, $escape_function = '')
136+
private function replace($string, $escape_function = 'esc_html')
138137
{
138+
// first, replace inside attributes
139+
$this->escape_function = 'esc_attr';
140+
$string = preg_replace_callback('/\=[\'"]?[^\'"]*\{(\w+)(\ +(?:(?!\{)[^}\n])+)*\
141+
}/', [ $this, 'replace_tag' ], $string);
142+
139143
$this->escape_function = $escape_function;
140144

141145
// replace strings like this: {tagname attr="value"}
142-
$string = preg_replace_callback('/\{(\w+)(\ +(?:(?!\{)[^}\n])+)*\}/', [ $this, 'replace_tag' ], $string);
146+
$string = preg_replace_callback('/\{(\w+)(\ +(?:(?!\{)[^}\n])+)*\
147+
}/', [ $this, 'replace_tag' ], $string);
143148

144149
// call again to take care of nested variables
145150
$string = preg_replace_callback('/\{(\w+)(\ +(?:(?!\{)[^}\n])+)*\}/', [ $this, 'replace_tag' ], $string);
@@ -193,7 +198,7 @@ protected function get_cookie($args = [])
193198
$default = isset($args['default']) ? $args['default'] : '';
194199

195200
if (isset($_COOKIE[ $name ])) {
196-
return esc_html(stripslashes($_COOKIE[ $name ]));
201+
return $_COOKIE[ $name ];
197202
}
198203

199204
return $default;
@@ -213,7 +218,7 @@ protected function get_user_property($args = [])
213218
$user = wp_get_current_user();
214219

215220
if ($user instanceof WP_User && isset($user->{$property})) {
216-
return esc_html($user->{$property});
221+
return $user->{$property};
217222
}
218223

219224
return $default;
@@ -245,7 +250,7 @@ protected function get_post_property($args = [])
245250
protected function get_email()
246251
{
247252
if (! empty($_REQUEST['EMAIL'])) {
248-
return strip_tags($_REQUEST['EMAIL']);
253+
return sanitize_email($_REQUEST['EMAIL']);
249254
}
250255

251256
// then , try logged-in user

includes/class-personal-data-exporter.php

100644100755
File mode changed.

includes/forms/class-form-tags.php

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -55,15 +55,15 @@ public function replace_in_form_content($string, MC4WP_Form $form, MC4WP_Form_El
5555
$this->form = $form;
5656
$this->form_element = $element;
5757

58-
$string = $this->replace($string);
58+
$string = $this->replace_in_html($string);
5959
return $string;
6060
}
6161

6262
public function replace_in_form_response($string, MC4WP_Form $form)
6363
{
6464
$this->form = $form;
6565

66-
$string = $this->replace($string);
66+
$string = $this->replace_in_html($string);
6767
return $string;
6868
}
6969

@@ -124,6 +124,6 @@ public function get_data(array $args = [])
124124
$value = join(', ', $value);
125125
}
126126

127-
return esc_html($value);
127+
return $value;
128128
}
129129
}

includes/forms/class-form.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -171,7 +171,7 @@ public function __construct($id, WP_Post $post, array $post_meta = [])
171171
*/
172172
public function __get($name)
173173
{
174-
$method_name = sprintf('get_%s', $name);
174+
$method_name = "get_$name";
175175
if (method_exists($this, $method_name)) {
176176
return $this->$method_name();
177177
}

includes/integrations/class-integration-tags.php

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -43,8 +43,7 @@ public function register()
4343
public function replace_in_checkbox_label($string, MC4WP_Integration $integration)
4444
{
4545
$this->integration = $integration;
46-
$string = $this->replace($string, 'esc_html');
47-
return $string;
46+
return $this->replace_in_html($string);
4847
}
4948

5049
/**

0 commit comments

Comments
 (0)