Comment protéger les pages avec une double authentification: mot de passe + e-mail (dans un champ personnalisé)


8

Je souhaite étendre la protection par mot de passe WordPress des publications en ajoutant un champ de saisie supplémentaire pour les e-mails des utilisateurs.

Ainsi, pour voir le contenu, l'utilisateur devra connaître le mot de passe et l'e-mail précédemment donné qui sont stockés dans le méta-champ personnalisé de la publication protégée.

J'essayais de trouver un bon crochet en vérifiant ce champ supplémentaire mais sans succès. Pourriez-vous me donner quelques idées pour le faire? Je ne veux pas créer de comptes utilisateur pour ce type de fonctionnalité.

Réponses:


7

Lorsque vous définissez une publication comme protégée par mot de passe, la protection se produit sur la get_the_content()fonction. Il WordPress recherche un cookie de mot de passe et s'il n'est pas défini, non valide ou expiré, affichez le formulaire de mot de passe.

Ce formulaire de mot de passe est envoyé à wp-login.php, un cookie est installé en fonction du mot de passe écrit dans le formulaire, puis la demande est redirigée vers la publication.

Le processus peut être décrit comme suit:

  1. aller à la page de publication
  2. appeler the_content ()
  3. vérifier le cookie
  4. si non valide montrer le formulaire de mot de passe
  5. soumettre le formulaire à wp_login.php
  6. wp_login.php
  7. définir le cookie basé sur pwd soumis et rediriger vers la page de publication
  8. recommencer le formulaire # 1

Ce que nous pouvons faire:

  • au point n ° 4, utilisez le crochet 'the_password_form'pour modifier la sortie du formulaire, en ajoutant un champ pour l'e-mail et un champ caché avec l'identifiant de publication (à ce stade, nous sommes à l'intérieur de la get_the_contentfonction, nous avons donc accès à la variable de publication globale)
  • Malheureusement, au point 3 , nous ne pouvons pas modifier le résultat de la vérification des cookies (ou du moins, nous ne pouvons pas le faire de manière simple et fiable). Mais au point # 7, WordPress a un crochet de filtre qui permet de définir l'expiration du cookie: si nous définissons cette heure sur un horodatage passé, alors le cookie ne sera pas défini (et s'il existex il sera supprimé) et donc la validation échouera . Nous pouvons donc utiliser ce crochet pour vérifier l'e-mail soumis via le formulaire et grâce à l'identifiant de publication dans le champ caché, nous pouvons le comparer avec les e-mails dans la méta, si l'e-mail n'est pas donné ou est incorrect, nous retournons un horodatage passé.

Premier pas:

/**
 * Customize the form, adding a field for email and a hidden field with the post id
 */
add_filter( 'the_password_form', function( $output ) {

  unset( $GLOBALS['the_password_form'] );
  global $post;
  $submit = '<input type="submit" name="Submit" value="' . esc_attr__('Submit') . '" /></p>';
  $hidden = '<input type="hidden" name="email_res_postid" value="' . $post->ID . '">';
  $email = '</p><p><label for="email_res">' . __( 'Email:' );
  $email .= '<input name="email_res" id="email_res" type="text" size="20" /></label></p><p>';
  return str_replace( $submit, $hidden . $email . $submit, $output );

}, 0 );

Et le deuxième:

/**
 * Set the post password cookie expire time based on the email
 */
add_filter( 'post_password_expires', function( $valid ) {

  $postid = filter_input( INPUT_POST, 'email_res_postid', FILTER_SANITIZE_NUMBER_INT );
  $email = filter_input( INPUT_POST, 'email_res', FILTER_SANITIZE_STRING );
  // a timestamp in the past
  $expired = time() - 10 * DAY_IN_SECONDS;
  if ( empty( $postid ) || ! is_numeric( $postid ) ) {
      // empty or bad post id, return past timestamp
      return $expired;
  }
  if ( empty($email) || ! filter_var($email, FILTER_VALIDATE_EMAIL) ) {
      // empty or bad email id, return past timestamp
      return $expired;
  }
  // get the allowed emails
  $allowed = array_filter( (array)get_post_meta( $postid, 'allow_email' ), function( $e ) {
    if ( filter_var( $e, FILTER_VALIDATE_EMAIL) ) return $e;
  });
  if ( ! empty( $allowed ) ) { // some emails are setted, let's check it
    // if the emails posted is good return the original expire time
    // otherwise  return past timestamp
    return in_array( $email, $allowed ) ? $valid : $expired;
  }
  // no emails are setted, return the original expire time
  return $valid;

}, 0 );

Nous avons fini.

Maintenant, créez un message, enregistrez-le comme protégé par mot de passe et définissez certains e-mails autorisés dans des champs personnalisés à l'aide de la clé 'allow_email'. Il n'y a pas de limite au nombre d'e-mails que vous pouvez ajouter ...


Réglages:

Champs personnalisés pour permettre la protection des messages électroniques


protection post via mot de passe


Résultat (TwentyThirteen sans style supplémentaire):

Résultat en TwentyThirteen sans style supplémentaire

En utilisant notre site, vous reconnaissez avoir lu et compris notre politique liée aux cookies et notre politique de confidentialité.
Licensed under cc by-sa 3.0 with attribution required.