Avec "magic quotes" désactivé, pourquoi PHP / Wordpress continue-t-il à auto-échapper à mes données POST?
c'est une question simple avec une réponse étrangement insaisissable.
get_magic_quotes_gpc()
rapports 0. Je répète, les guillemets magiques sont éteints. Les guillemets magiques semblent avoir été désactivés dans php.ini
(pas à l'exécution).
néanmoins, toutes les données POST y compris les guillemets simples (') sont échappées lorsqu'on y accède en PHP. Ce pourrait être la cause?
je vous Remercie.
Modifier: Pour les curieux, voici une capture d'écran de notre phpinfo: http://img843.imageshack.us/img843/6959/screenshot20120120at552.png
Edit: lors de la préparation d'un cas de test, j'ai découvert l'origine générale du problème. Nous sommes en train de Bootstrapper Wordpress car notre application s'intègre avec une installation multi-site WP. Lorsque je désactive le bootstrapping Wordpress, l'Auto-Escape est désactivé. Est-ce que quelqu'un sait où le code Auto-escape de Wordpress peut être localisé?
6 réponses
je pense que je l'ai trouvé. Problème (bug): http://core.trac.wordpress.org/ticket/18322
Solution:http://codex.wordpress.org/Function_Reference/stripslashes_deep
$_GET = array_map('stripslashes_deep', $_GET);
$_POST = array_map('stripslashes_deep', $_POST);
$_COOKIE = array_map('stripslashes_deep', $_COOKIE);
$_SERVER = array_map('stripslashes_deep', $_SERVER);
$_REQUEST = array_map('stripslashes_deep', $_REQUEST);
Note: Comme suggéré par @Alexandar O'Mara, vous pourriez vouloir reconsidérer la réécriture des superglobaux comme ceci. Si cela est approprié pour votre situation, par exemple, vous pourriez simplement "strip localement" en utilisant une alternative comme $post = array_map('stripslashes_deep', $_POST);
développer la réponse de @rinogo avec une explication plus profonde, et proposer une autre solution.
wp-settings.php il y a un inconditionel wp_magic_quotes
// Add magic quotes and set up $_REQUEST ( $_GET + $_POST )
wp_magic_quotes();
Wordpress échappe citations peu importe ce que
function wp_magic_quotes() {
// If already slashed, strip.
// Escape with wpdb.
// Force REQUEST to be GET + POST.
}
ce qui est intéressant cependant est cet appel est fait après les plugins ont été chargés,avant le thème est chargé. Sooo, au sommet de votre plugin
// A hack to cope with un-configurable call to wp_magic_quotes
// E.G. Make the original $_POST available through a global $_REAL_POST
$_REAL_GET = $_GET;
$_REAL_POST = $_POST;
$_REAL_COOKIE = $_COOKIE;
$_REAL_REQUEST = $_REQUEST;
alors vous pouvez librement utiliser $_REAL_POST
et al à la place de $_POST
(en se souvenant que c'est un global pas superglobale) où vous devez. Rappelez-vous aussi que pendant que votre plugin a chargé avant le thème, si le thème appelle vers le bas dans l'une des fonctions du plugin qui utilise $_POST
, il faut lire à partir de $_REAL_POST
pour obtenir les valeurs non escapadrées.
la meilleure réponse fournie ici est de copier pour usage personnel comme:
$post = array_map('stripslashes_deep', $_POST);
il y a un problème théorique avec cela cependant: puisque vous travaillez avec un duplicata, vous ne pouvez pas persister des changements aux superglobaux (hé, Je ne dis pas que c'est une bonne pratique, d'accord?).
Solution: méthodes accessor
dans une tentative de résoudre ce gâchis d'une manière définie et sans aucun effet secondaire, j'ai fait des "méthodes accessor" qui s'appliquent de façon transparente stripslashes_deep()
ou addslashes_deep()*
pour obtenir/définir des demandes à la suite de tableaux superglobaux:
* j'ai dû jeter addslashes_deep()
ensemble de WordPress stripslashes_deep()
.
$_GET
$_POST
$_COOKIE
$_SERVER
$_REQUEST
Vous pouvez les utiliser comme:
echo _get('username'); // echo stripslashes_deep($_GET['username']);
_cookie('name', 'value'); // $_COOKIE['name'] = addslashes_deep('value');
Voici le code (je l'appelle gpcsr.php
):
<?php
// cat stripslashes_deep() | sed 's/stripslashes/addslashes/g'
function addslashes_deep( $value ) {
if ( is_array($value) ) {
$value = array_map('addslashes_deep', $value);
} elseif ( is_object($value) ) {
$vars = get_object_vars( $value );
foreach ($vars as $key=>$data) {
$value->{$key} = addslashes_deep( $data );
}
} elseif ( is_string( $value ) ) {
$value = addslashes($value);
}
return $value;
}
function _generic_slashes_wrap(&$arr, $key, $value = null) {
if (func_num_args() === 2) return stripslashes_deep($arr[$key]);
else $arr[$key] = addslashes_deep($value);
}
function _get ($key, $value = null) { if (func_num_args() === 1) return _generic_slashes_wrap($_GET, $key); else _generic_slashes_wrap($_GET, $key, $value); }
function _post ($key, $value = null) { if (func_num_args() === 1) return _generic_slashes_wrap($_POST, $key); else _generic_slashes_wrap($_POST, $key, $value); }
function _cookie ($key, $value = null) { if (func_num_args() === 1) return _generic_slashes_wrap($_COOKIE, $key); else _generic_slashes_wrap($_COOKIE, $key, $value); }
function _server ($key, $value = null) { if (func_num_args() === 1) return _generic_slashes_wrap($_SERVER, $key); else _generic_slashes_wrap($_SERVER, $key, $value); }
function _request ($key, $value = null) { if (func_num_args() === 1) return _generic_slashes_wrap($_REQUEST, $key); else _generic_slashes_wrap($_REQUEST, $key, $value); }
?>
j'ai juste eu à faire face à cette question et j'ai trouvé ce que je pense être une bonne solution. Il s'assure que l'adresse gpcs sont jamais revues à la baisse. J'ai juste mis ça en haut de mon plugin (ça marcherait aussi en haut d'un thème, je pense):
add_action( 'init', 'unslash_gpc' );
function unslash_gpc() {
$_GET = array_map('stripslashes_deep', $_GET);
$_POST = array_map('stripslashes_deep', $_POST);
$_COOKIE = array_map('stripslashes_deep', $_COOKIE);
$_SERVER = array_map('stripslashes_deep', $_SERVER);
$_REQUEST = array_map('stripslashes_deep', $_REQUEST);
}
Et maintenant, tout est parfait!
Wordpress fournit une solution pour cela en utilisant la fonction wordpress stripslashes_deep. Ainsi, les bribes mentionnés dans la réponse de @rinogo deviendraient :
$_GET = stripslashes_deep($_GET);
$_POST = stripslashes_deep($_POST);
$_COOKIE = stripslashes_deep($_COOKIE);
$_REQUEST = stripslashes_deep($_REQUEST);
$_SERVER variable globale, donc je suppose qu'elle n'est pas affectée.
WordPress ajoute des slashs à $_POST/$_GET/$_REQUEST / $_COOKIE indépendamment de ce que get_magic_quotes_gpc() retourne. Dans le contexte de WordPress, stripslashes() ou stipslashes_deep () doivent toujours être utilisés lors de l'utilisation de ces variables.
Ou, il suffit de faire comme j'ai fait. Commentez toute l'implémentation dans load.la méthode wp_magic_quotes() de php.
Je n'ai pas besoin de citations magiques. Cela me causait bien plus de maux de tête que cela ne valait la peine. Personnellement, je préfère maintenir ma propre discipline de l'hygiène d'entrée. Je ne veux pas commencer à avoir de mauvaises habitudes de programmation.
mais, je comprends la compulsion de WordPress pour inclure une telle "fonctionnalité". Peut-être que la communauté du développement serait mieux servie une option pour le désactiver.