web-dev-qa-db-fra.com

Approche correcte pour valider la saisie d'un champ personnalisé

J'ai un type de message personnalisé avec plusieurs champs personnalisés. Je cherche à valider ces champs car ils seront utilisés en aval par d'autres services. Il est donc important qu’il ne puisse pas être sauvegardé tant qu’il n’a pas été entré correctement. La validation est relativement complexe et nécessite une logique personnalisée.

Malheureusement, l'utilisation d'un plugin dans ce cas particulier ne fonctionnera pas non plus.

Y a-t-il un crochet idéal à utiliser dans ce cas? À un niveau élevé - quelle est la meilleure façon de s'y prendre.

3
Ethan Seifert

Exemple de code dans add_meta_box() la documentation utilise save_post hook (à la toute fin de wp_insert_post() ) pour ajouter des données de champs personnalisés à partir de metabox.

Vous devez déjà utiliser quelque chose comme ça dans vos métaboxes, n’est-ce pas un endroit approprié pour valider vos données? ..

4
Rarst

(Tiré de ma réponse à une question similaire postée ici )

Cette méthode comporte deux étapes: premièrement, une fonction pour enregistrer les données de votre champ metabox personnalisé (raccordé à save_post), et deuxièmement, une fonction pour lire le nouveau post_meta (que vous venez de sauvegarder), le valider et modifier le résultat de enregistrer si nécessaire (également relié à save_post, mais après le premier). Si la validation échoue, la fonction validateur modifie le post_status de nouveau à "en attente", empêchant ainsi la publication de la publication.

Étant donné que la fonction save_post est appelée beaucoup, chaque fonction a des vérifications à exécuter uniquement lorsque l'utilisateur veut publier, et uniquement pour votre type de publication personnalisé (mycustomtype).

J'ajoute aussi généralement des messages de notification personnalisés pour aider l'utilisateur à comprendre pourquoi son message n'a pas été publié, mais ceux-ci sont devenus un peu compliqués à inclure ici ...

add_action('save_post', 'save_my_fields', 10, 2);
add_action('save_post', 'completion_validator', 20, 2);

function save_my_fields($pid, $post) {
    // don't do on autosave or when new posts are first created
    if ( ( defined( 'DOING_AUTOSAVE' ) && DOING_AUTOSAVE ) || $post->post_status == 'auto-draft' ) return $pid;
    // abort if not my custom type
    if ( $post->post_type != 'mycustomtype' ) return $pid;

    // save post_meta with contents of custom field
    update_post_meta($pid, 'mymetafield', $_POST['mymetafield']);
}


function completion_validator($pid, $post) {
    // don't do on autosave or when new posts are first created
    if ( ( defined( 'DOING_AUTOSAVE' ) && DOING_AUTOSAVE ) || $post->post_status == 'auto-draft' ) return $pid;
    // abort if not my custom type
    if ( $post->post_type != 'mycustomtype' ) return $pid;

    // init completion marker (add more as needed)
    $meta_missing = false;

    // retrieve meta to be validated
    $mymeta = get_post_meta( $pid, 'mymetafield', true );
    // just checking it's not empty - you could do other tests...
    if ( empty( $mymeta ) ) {
        $meta_missing = true;
    }

    // on attempting to publish - check for completion and intervene if necessary
    if ( ( isset( $_POST['publish'] ) || isset( $_POST['save'] ) ) && $_POST['post_status'] == 'publish' ) {
        //  don't allow publishing while any of these are incomplete
        if ( $meta_missing ) {
            global $wpdb;
            $wpdb->update( $wpdb->posts, array( 'post_status' => 'pending' ), array( 'ID' => $pid ) );
            // filter the query URL to change the published message
            add_filter( 'redirect_post_location', create_function( '$location','return add_query_arg("message", "4", $location);' ) );
        }
    }
}

Pour plusieurs champs metabox, ajoutez simplement plus de marqueurs de complétion, récupérez plus de post_meta et effectuez plus de tests.

1
somatic