J'ai écrit un plugin qui crée un type d'article personnalisé avec des champs personnalisés. Pour empêcher les utilisateurs d'entrer des informations incorrectes, comment puis-je valider les données?
J'ai supposé que la fonction de hook save_post traiterait la validation de champ, mais je n'arrive pas à trouver un moyen simple d'afficher les erreurs à l'utilisateur.
Existe-t-il une fonction Wordpress intégrée pour cela? Quelle est la technique générale pour accomplir la validation de champ personnalisée?
Vous êtes sur la bonne voie. Je teste les champs dans le callback save_post
, puis j'utilise admin notices pour afficher les erreurs à l'attention de l'utilisateur lorsqu'un champ ne parvient pas à être validé. Ils apparaissent uniquement dans une zone en surbrillance en haut de la page, tout comme les erreurs/messages générés par WordPress.
Voici un exemple simple de création d'un avis d'administrateur:
function my_admin_notice()
{
?>
<div class="updated">
<p>Aenean eros ante, porta commodo lacinia.</p>
</div>
<?php
}
add_action( 'admin_notices', 'my_admin_notice' );
Ce n'est pas très pratique, cependant. Dans une situation comme celle-ci, vous voulez simplement une fonction à laquelle vous pouvez transmettre un message. Quelque chose comme,
if( $pizza != 'warm' )
$notices->enqueue( 'Pizza is not warm', 'error' );
Ainsi, vous pouvez écrire cette fonction enqueue()
vous-même (avec une fonction permettant d’imprimer les avis), ou vous pouvez inclure une bibliothèque telle que IDAdminNotices .
Voici un exemple de un plugin que j'ai écrit . Cela utilise les fonctions de mise en file d'attente/d'impression de notification intégrées à la classe elle-même, plutôt que d'inclure une bibliothèque externe.
public function saveCustomFields( $postID )
{
// ...
if( filter_var( $_POST[ self::PREFIX . 'zIndex'], FILTER_VALIDATE_INT ) === FALSE )
{
update_post_meta( $post->ID, self::PREFIX . 'zIndex', 0 );
$this->enqueueMessage( 'The stacking order has to be an integer.', 'error' );
}
else
update_post_meta( $post->ID, self::PREFIX . 'zIndex', $_POST[ self::PREFIX . 'zIndex'] );
// ...
}
add_action( 'save_post', array( $this, 'saveCustomFields' );
J'ai écrit un petit plugin qui non seulement valide les champs de saisie sur les types de publication personnalisés, mais supprime également la notification de l'administrateur par défaut, sans utiliser Javascript.
voici une partie du code
/ Filtres de validation
$title = $album->post_title;
if ( ! $title ) {
$errors['title'] = "The title is required";
}
// if we have errors lets setup some messages
if (! empty($errors)) {
// we must remove this action or it will loop for ever
remove_action('save_post', 'album_save_post');
// save the errors as option
update_option('album_errors', $errors);
// Change post from published to draft
$album->post_status = 'draft';
// update the post
wp_update_post( $album );
// we must add back this action
add_action('save_post', 'album_save_post');
// admin_notice is create by a $_GET['message'] with a number that wordpress uses to
// display the admin message so we will add a filter for replacing default admin message with a redirect
add_filter( 'redirect_post_location', 'album_post_redirect_filter' );
}
Vous pouvez voir le tutoriel complet ici
save_post
est exécuté, la publication a déjà été enregistrée dans la base de données.Si vous utilisez ACF, sa validation est intégrée.
Toutefois, si vous devez valider des éléments extérieurs à ACF, tels que post_title, les choses se compliquent un peu.
En examinant le code principal de WordPress, plus particulièrement la fonction update_post()
du wp-includes/post.php
, il n’existe aucun moyen intégré d’intercepter une demande avant son enregistrement dans la base de données.
Cependant, nous pouvons accrocher pre_post_update
et utiliser header()
et get_post_edit_link()
pour empêcher la publication de la publication.
<?php
/**
* Performs custom validation on custom post type "Site"
*/
function custom_post_site_save($post_id, $post_data) {
# If this is just a revision, don't do anything.
if (wp_is_post_revision($post_id))
return;
if ($post_data['post_type'] == 'site') {
# In this example, we will deny post titles with less than 5 characters
if (strlen($post_data['post_title'] < 5)) {
# Add a notification
update_option('my_notifications', json_encode(array('error', 'Post title can\'t be less than 5 characters.')));
# And redirect
header('Location: '.get_edit_post_link($post_id, 'redirect'));
exit;
}
}
}
add_action( 'pre_post_update', 'custom_post_site_save', 10, 2);
/**
* Shows custom notifications on wordpress admin panel
*/
function my_notification() {
$notifications = get_option('my_notifications');
if (!empty($notifications)) {
$notifications = json_decode($notifications);
#notifications[0] = (string) Type of notification: error, updated or update-nag
#notifications[1] = (string) Message
#notifications[2] = (boolean) is_dismissible?
switch ($notifications[0]) {
case 'error': # red
case 'updated': # green
case 'update-nag': # ?
$class = $notifications[0];
break;
default:
# Defaults to error just in case
$class = 'error';
break;
}
$is_dismissable = '';
if (isset($notifications[2]) && $notifications[2] == true)
$is_dismissable = 'is_dismissable';
echo '<div class="'.$class.' notice '.$is_dismissable.'">';
echo '<p>'.$notifications[1].'</p>';
echo '</div>';
# Let's reset the notification
update_option('my_notifications', false);
}
}
add_action( 'admin_notices', 'my_notification' );