Sanitization of Fields input
- This topic has 29 replies, 6 voices, and was last updated 5 years ago by
david.h.
-
AuthorPosts
-
August 15, 2019 at 11:21 PM #15709
david.h
ParticipantHi Anh,
Good job prioritising this - my feedback:
First:
It would be best if all data entry points are sanitized with the most appropriate WordPress function, so this would mean textarea would utilise 'sanitize_textarea_field':
https://developer.wordpress.org/reference/functions/sanitize_textarea_field/
Second:
For any field employing 'wp_kses_post' (WYSIWYG or Custom), allow developers to pass an optional sub-array of tags/protocols to be allowed using:
https://codex.wordpress.org/Plugin_API/Filter_Reference/pre_kses
which is principally based on:
https://codex.wordpress.org/Function_Reference/wp_kses_allowed_html
Third:
Enforce a minimum of 'sanitize_textarea_field' to all custom field types and allow developers to change this, but limited to only one of the built-in WordPress sanitization functions.
Fourth:
Allow developers to bypass WordPress security altogether, (obviously not advised) and implement their own sanitization.
This should only be enabled if a developer (understanding the risks) changes the default setting of sanitize:true to sanitize:custom_callback and provides a working callback function.
Hope this helps,
DavidAugust 15, 2019 at 11:48 PM #15711Anh Tran
KeymasterHi David,
Thanks for your feedback. Yes, I want to complete this thing as it's important and I don't want to postpone at the middle.
Regarding your feedback:
- I think sanitize_textarea_field is too limited. It seems fine with the function name, but people usually use it for HTML content. I'm using wp_kses_post, which I think is okay.
- Adding params for wp_kses_post can be done. But it will make the code more complicated in both plugin's side and developer's side. I think in this case, developers can do that easier with a custom sanitize callback like this:
'sanitize_callback' => function( $value ) { $allowed_tags = []; return wp_kses( $value, $allowed_tags ); }
- I'm thinking about this, too. Need to find a good way to implement that without breaking things.
- That's available via custom
sanitize_callback
param (see the example above). Developers can define their own sanitize callback or bypass the sanitization with this code:
'sanitize_callback' => function( $value ) { return $value; }
August 16, 2019 at 12:30 AM #15714david.h
ParticipantOk, although I'm not really sure what feedback you are looking for?
1) sanitize_textarea_field is for a textarea field which should be used as per https://developer.mozilla.org/en-US/docs/Web/HTML/Element/textarea
2) I'm not sure this would be more complicated, its simply a nested array passed to a function which you have already outlined.
August 16, 2019 at 9:08 AM #15719Anh Tran
KeymasterHi David,
Your feedback is great and that's exactly what I'm looking for. My reply above was just a discussion about your ideas.
I'll consider your suggestions. Thanks.
August 17, 2019 at 3:12 PM #15730Anh Tran
KeymasterHey guys,
I finish the code for the sanitizer part.
It works like this:
- Sanitization is auto applied for all built-in types.
- For custom field types, developers needs to implement their sanitization via
sanitize_callback
parameter. If no sanitize callback is provided, the field won't be sanitize. I do this to not break the websites at the moment. In the future, I might add default sanitization for all custom field types ifsanitize_callback
is not defined. At this stage, I think this is enough. - Developers can also bypass sanitization by setting
'sanitize_callback' => 'none'
(if set to a callable, it will be used for sanitization).
I'll merge the commits and release a new version for Meta Box next week.
Thank you all for your feedback!
January 25, 2020 at 5:30 AM #18005[email protected]
ParticipantI was able to bypass the sanitization of the textarea field in the sanatize.php file
/**
'textarea' => 'wp_kses_post',
*/but of course when the metabox plugin gets updated that file will be overwriten.
I'm not a coder, could you provide me a code snippet I can paste into the child theme functions.php file to disable sanitization for the textarea field?
Thanks, love your plugin and the support you provide.
Pieter
January 25, 2020 at 7:26 PM #18007Anh Tran
KeymasterHi Pieter, please see my reply above and the documentation.
April 17, 2020 at 6:50 AM #19082Austin Passy
ParticipantIs there a reason
textarea
is usingwp_kses_post
oversanitize_textarea_field
?April 17, 2020 at 11:35 AM #19089Long Nguyen
ModeratorHi Austin,
By default, the field
textarea
useswp_kses_post
as the callback function to sanitize as we've noted in the documentation.This function allows you to insert the HTML tag
<style>
<script>
such as custom CSS, JS code in the settings page whilesanitize_textarea_field
strips all tags.For more information, please follow the documentation
https://developer.wordpress.org/reference/functions/wp_kses_post/
https://developer.wordpress.org/reference/functions/sanitize_textarea_field/April 17, 2020 at 7:27 PM #19099david.h
ParticipantHi Long/Anh,
Normally I would not reply to an ostensibly "resolved" thread, but this is security related and should not be ignored any longer. There needs to be a solution to the issue you are grappling with which, primarily, seems to be allowing developers to embed HTML in a page using Metabox fields.
This should be done using a specific, preferably dedicated, field type (e.g. HTML or custom) where the sanitation is more relaxed - i.e. wp_kses_post.
The average user should not have to consider whether Metabox has correctly handled sanitization for their custom fields. So, when they create a textarea field (for it's intended purpose - text), this should not be open to abuse by unscrupulous users or bots posting HTML, scripts or suchlike.
Thus, as has been suggested several times in this post, all Metabox fields should be sanitized using the most appropriate WordPress function - i.e. in this instance, sanitize_textarea_field.
Please can you come up with a solid solution.
April 17, 2020 at 7:48 PM #19100Rao Abid
ParticipantHi @david.h,
i have been working for the sansitization for long and i understand the position of the developer of the Metabox as well as they need to take into consideration backward compatibility as well.
If you remember i was the one who pointed this out and wanted Metabox to do sanitization out-of-the-box.
You may get surprised to know that ACF still does not apply such sanitization out-of-the-box.
In my opinion, its all fine if a textarea is sanitized using the
wp_kses_post
instead of more appropriatesanitize_textarea_field
.The reasons being two:
1. Backward compatibility is important, no developer wants to get the support system flooded with angry users who claiming to be something broken due to a new update.
2. Developer who are using this framework should get themselves familiar with the habit of understanding what the framework does out-of-box and they have the option to override the sanitization functions with the help of filter. If they are two lazy to add a line of code for sanitization of their choice, then they should seriously consider their habits of blindly using any framework/plugin found on the wild internet.Just my two cents.
I know you oppose this approach and more like strict sainitization out-of-box, but please consider all half million developers/users who might be using the textarea field for their custom css code.
Many thanks,
sorry if our opinions does not match.
Regards,
Rao Abid
April 17, 2020 at 10:31 PM #19102Anh Tran
KeymasterHi guys,
Rao pointed some valid point over the decision.
I want to clarify that:
sanitize_textarea_field
is the best fortextarea
field from the developer point of view and I agree with that. However, there are some reasons we consider usingwp_kses_post
as the default sanitize callback:First: from user point of view, as David said, they don't know what happen behind the scene. And in fact, they do use
textarea
for storing HTML a lot! Something like footer credit or some text for the top bar. Some even use it for embeded videos. We see this behavior all the time. So we decide to usewp_kses_post
to bring more comfort to users. Note that, this doesn't mean less secured! Bothwp_kses_post
andsanitize_textarea_field
are secured (and that's the main point of the sanitization). We need to keep balance between comfort and strictness.Second: as Rao said, backward compatibility is important. Being activated on 500k sites, we don't want to get thousands of complaints and support topics for the same broken textarea. In fact, there are many topics here and on wordpress.org forums asking why their textarea field not working as expected (because they store embeded videos HTML code).
I can say, if I build Meta Box again from scratch,
sanitize_textarea_field
might be the best choice. But at this time,wp_kses_post
is a better choice.And remember, they're both secured. That's the main point.
April 17, 2020 at 11:53 PM #19103david.h
ParticipantOk,
I think we are focusing on entirely differing viewpoints: back-end vs front-end.
My understanding is that historically Metabox allowed HTML to be posted in textarea fields to aid developers, as Anh says in #19102. However, my concern is for the thousands of new/novice developers who are now using Metabox without detailed knowledge of what is happening in the background.
Since the introduction of MB FrontEnd Submission, many people will be creating public facing front-end forms (e.g. contact, listings, etc) many of which can be submitted without credentials or authentication. Thus, removing all tags and only allowing text in a textarea is what any reasonable person would expect from framework that proclaims "The sleepless nights of endless coding are over". If true, this is a comforting statement, but to be so Metabox must keep patrons' security above aesthetics, ease of function or endlessly accommodating backwards compatibility.
For all the time we've spent discussing this, there could have been a number of relatively simple workarounds implemented - e.g. passing MB FrontEnd Submission textarea fields through sanitize_textarea_field before the default Metabox sanitization of wp_kses_post kicks in - clearly this is not carefully considered solution, but it would work for an interim period of time.
In the WordPress ecosystem, we have all encountered too many sites that have been compromised by plugins devoid of appropriate or adequate security, so please let's try and start something new here - security comes first.
I hope that this thread has opened discussion and thinking that might not have occurred otherwise.
All the best
April 18, 2020 at 7:20 AM #19107Anh Tran
KeymasterHi David,
Allowing HTML in textarea doesn't mean less secured. In fact, it's the recommended way to sanitize content that contains HTML. WordPress is smart enough to filter the allowed HTML tags based on the role of the current user. Using it actually prevents websites from being compromised. So, I think no problems using it on the frontend.
PS: The topic is always open for discussion.
April 19, 2020 at 9:56 PM #19114david.h
ParticipantHi Anh,
I had server hacked once (through a poorly secured web app), so now I'm far more careful.
Try reading through:
https://www.cisecurity.org/controls/cis-controls-list/
Specifically, Control 4 and the principal of least privilege:
https://www.cisecurity.org/spotlight/ei-isac-cybersecurity-spotlight-principle-of-least-privilege/
IMO, this principle should be applied to all dev scenarios, including sanitize_textarea or wp_kses.
Thanks
-
AuthorPosts
- You must be logged in to reply to this topic.