Skip to content

Commit

Permalink
feat(reader-activation): customizable account deletion, password rese…
Browse files Browse the repository at this point in the history
…t emails (#1938)
  • Loading branch information
adekbadek authored Sep 1, 2022
1 parent 2547b76 commit c121e5c
Show file tree
Hide file tree
Showing 9 changed files with 458 additions and 108 deletions.
62 changes: 35 additions & 27 deletions includes/emails/class-emails.php
Original file line number Diff line number Diff line change
Expand Up @@ -160,31 +160,13 @@ public static function register_meta() {
}

/**
* Send an HTML email.
* Get email payload by config name.
*
* @param string|int $config_name_or_post_id Email config name or email post ID.
* @param string $to Recipient's email addesss.
* @param array $placeholders Dynamic content substitutions.
* @param string $config_name Name of email config.
* @param array $placeholders Placeholders to replace in email.
*/
public static function send_email( $config_name_or_post_id, $to, $placeholders = [] ) {
if ( ! self::supports_emails() ) {
return false;
}

$switched_locale = \switch_to_locale( \get_user_locale( \wp_get_current_user() ) );
$email_config_name = $config_name_or_post_id;

if ( 'string' === gettype( $config_name_or_post_id ) ) {
$email_config = self::get_email_config_by_type( $config_name_or_post_id );
} elseif ( 'integer' === gettype( $config_name_or_post_id ) ) {
$email_config = self::serialize_email( null, $config_name_or_post_id );
$email_config_name = \get_post_meta( $config_name_or_post_id, self::EMAIL_CONFIG_NAME_META, true );
} else {
return false;
}
if ( ! $to || ! $email_config || 'publish' !== $email_config['status'] ) {
return false;
}
public static function get_email_payload( $config_name, $placeholders = [] ) {
$email_config = self::get_email_config_by_type( $config_name );
$html = $email_config['html_payload'];
$from_email = $email_config['from_email'];
$placeholders = array_merge(
Expand All @@ -211,6 +193,32 @@ public static function send_email( $config_name_or_post_id, $to, $placeholders =
$html
);
}
return $html;
}

/**
* Send an HTML email.
*
* @param string $config_name Email config name.
* @param string $to Recipient's email addesss.
* @param array $placeholders Dynamic content substitutions.
*/
public static function send_email( $config_name, $to, $placeholders = [] ) {
if ( ! self::supports_emails() ) {
return false;
}

$switched_locale = \switch_to_locale( \get_user_locale( \wp_get_current_user() ) );

if ( 'string' === gettype( $config_name ) ) {
$email_config = self::get_email_config_by_type( $config_name );
} else {
return false;
}
if ( ! $to || ! $email_config || 'publish' !== $email_config['status'] ) {
return false;
}

$email_content_type = function() {
return 'text/html';
};
Expand All @@ -219,9 +227,9 @@ public static function send_email( $config_name_or_post_id, $to, $placeholders =
$email_send_result = wp_mail( // phpcs:ignore WordPressVIPMinimum.Functions.RestrictedFunctions.wp_mail_wp_mail
$to,
$email_config['subject'],
$html,
self::get_email_payload( $config_name, $placeholders ),
[
sprintf( 'From: %s <%s>', $email_config['from_name'], $from_email ),
sprintf( 'From: %s <%s>', $email_config['from_name'], $email_config['from_email'] ),
]
);
remove_filter( 'wp_mail_content_type', $email_content_type );
Expand All @@ -230,7 +238,7 @@ public static function send_email( $config_name_or_post_id, $to, $placeholders =
\restore_previous_locale();
}

Logger::log( 'Sending "' . $email_config_name . '" email to: ' . $to );
Logger::log( 'Sending "' . $config_name . '" email to: ' . $to );

return $email_send_result;
}
Expand Down Expand Up @@ -365,7 +373,7 @@ public static function get_from_name() {
*
* @param string $type Type of the email.
*/
private static function get_email_config_by_type( $type ) {
public static function get_email_config_by_type( $type ) {
$emails_query = new \WP_Query(
[
'post_type' => self::POST_TYPE,
Expand Down
36 changes: 32 additions & 4 deletions includes/reader-activation/class-reader-activation-emails.php
Original file line number Diff line number Diff line change
Expand Up @@ -14,8 +14,10 @@
*/
class Reader_Activation_Emails {
const EMAIL_TYPES = [
'VERIFICATION' => 'reader-activation-verification',
'MAGIC_LINK' => 'reader-activation-magic-link',
'VERIFICATION' => 'reader-activation-verification',
'MAGIC_LINK' => 'reader-activation-magic-link',
'RESET_PASSWORD' => 'reader-activation-reset-password',
'DELETE_ACCOUNT' => 'reader-activation-delete-account',
];

/**
Expand All @@ -33,7 +35,7 @@ public static function init() {
* @param array $configs Email types.
*/
public static function add_email_configs( $configs ) {
$configs[ self::EMAIL_TYPES['VERIFICATION'] ] = [
$configs[ self::EMAIL_TYPES['VERIFICATION'] ] = [
'name' => self::EMAIL_TYPES['VERIFICATION'],
'label' => __( 'Verification', 'newspack' ),
'description' => __( "Email sent to the reader after they've registered.", 'newspack' ),
Expand All @@ -46,7 +48,7 @@ public static function add_email_configs( $configs ) {
],
],
];
$configs[ self::EMAIL_TYPES['MAGIC_LINK'] ] = [
$configs[ self::EMAIL_TYPES['MAGIC_LINK'] ] = [
'name' => self::EMAIL_TYPES['MAGIC_LINK'],
'label' => __( 'Login link', 'newspack' ),
'description' => __( 'Email with a login link.', 'newspack' ),
Expand All @@ -59,6 +61,32 @@ public static function add_email_configs( $configs ) {
],
],
];
$configs[ self::EMAIL_TYPES['RESET_PASSWORD'] ] = [
'name' => self::EMAIL_TYPES['RESET_PASSWORD'],
'label' => __( 'Reset Password', 'newspack' ),
'description' => __( 'Email with password reset link.', 'newspack' ),
'template' => dirname( NEWSPACK_PLUGIN_FILE ) . '/includes/templates/reader-activation-emails/password-reset.php',
'editor_notice' => __( 'This email will be sent to a reader when they request a password reset.', 'newspack' ),
'available_placeholders' => [
[
'label' => __( 'the password reset link', 'newspack' ),
'template' => '*PASSWORD_RESET_LINK*',
],
],
];
$configs[ self::EMAIL_TYPES['DELETE_ACCOUNT'] ] = [
'name' => self::EMAIL_TYPES['DELETE_ACCOUNT'],
'label' => __( 'Delete Account', 'newspack' ),
'description' => __( 'Email with account deletion link.', 'newspack' ),
'template' => dirname( NEWSPACK_PLUGIN_FILE ) . '/includes/templates/reader-activation-emails/delete-account.php',
'editor_notice' => __( 'This email will be sent to a reader when they request an account deletion.', 'newspack' ),
'available_placeholders' => [
[
'label' => __( 'the account deletion link', 'newspack' ),
'template' => '*DELETION_LINK*',
],
],
];
return $configs;
}
}
Expand Down
42 changes: 38 additions & 4 deletions includes/reader-activation/class-reader-activation.php
Original file line number Diff line number Diff line change
Expand Up @@ -67,7 +67,8 @@ public static function init() {
\add_action( 'template_redirect', [ __CLASS__, 'process_auth_form' ] );
\add_filter( 'amp_native_post_form_allowed', '__return_true' );
\add_filter( 'woocommerce_email_actions', [ __CLASS__, 'disable_woocommerce_new_user_email' ] );
\add_filter( 'retrieve_password_notification_email', [ __CLASS__, 'password_reset_email_from' ] );
\add_filter( 'retrieve_password_notification_email', [ __CLASS__, 'password_reset_configuration' ] );
\add_action( 'lostpassword_post', [ __CLASS__, 'set_password_reset_mail_content_type' ] );
}
}

Expand Down Expand Up @@ -1319,14 +1320,47 @@ function( $type ) {
*
* @return array The filtered $args.
*/
public static function password_reset_email_from( $args ) {
public static function password_reset_configuration( $args ) {
$config_name = Reader_Activation_Emails::EMAIL_TYPES['RESET_PASSWORD'];
$email_config = Emails::get_email_config_by_type( $config_name );

$args['headers'] = sprintf(
'From: %1$s <%2$s>',
Emails::get_from_name(),
Emails::get_from_email()
$email_config['from_name'],
$email_config['from_email']
);

$args['subject'] = $email_config['subject'];

$found_the_link = \preg_match(
'/.*wp-login\.php\?action=rp.*/',
$args['message'],
$matches
);
if ( $found_the_link ) {
$password_reset_url = $matches[0];
$args['message'] = Emails::get_email_payload(
$config_name,
[
[
'template' => '*PASSWORD_RESET_LINK*',
'value' => $password_reset_url,
],
]
);
}

return $args;
}

/**
* Set email content type when a password reset email is about to be sent.
*/
public static function set_password_reset_mail_content_type() {
$email_content_type = function() {
return 'text/html';
};
add_filter( 'wp_mail_content_type', $email_content_type );
}
}
Reader_Activation::init();
Original file line number Diff line number Diff line change
Expand Up @@ -193,57 +193,17 @@ public static function handle_delete_account_request() {
);
\set_transient( 'np_reader_account_delete_' . $user_id, $token, DAY_IN_SECONDS );

/* translators: %s User display name. */
$message = sprintf( __( 'Hello, %s!', 'newspack' ), $user->display_name ) . "\r\n\r\n";
$message .= __( 'To delete your account, follow the instructions in the following address:', 'newspack' ) . "\r\n\r\n";
$message .= $url . "\r\n";

$blogname = \wp_specialchars_decode( get_option( 'blogname' ), ENT_QUOTES );

$switched_locale = \switch_to_locale( get_user_locale( $user ) );

$email = [
'to' => $user->user_email,
/* translators: %s Site title. */
'subject' => __( '[%s] Account deletion request', 'newspack' ),
'message' => $message,
'headers' => [
sprintf(
'From: %1$s <%2$s>',
Emails::get_from_name(),
Emails::get_from_email()
),
],
];

/**
* Filters the account deletion email.
*
* @param array $email Email arguments. {
* Used to build wp_mail().
*
* @type string $to The intended recipient - New user email address.
* @type string $subject The subject of the email.
* @type string $message The body of the email.
* @type string $headers The headers of the email.
* }
* @param \WP_User $user User to send the magic link to.
* @param string $url Account deletion form url.
*/
$email = \apply_filters( 'newspack_reader_account_delete_email', $email, $user, $url );

// phpcs:ignore WordPressVIPMinimum.Functions.RestrictedFunctions.wp_mail_wp_mail
$sent = \wp_mail(
$email['to'],
\wp_specialchars_decode( sprintf( $email['subject'], $blogname ) ),
$email['message'],
$email['headers']
$sent = Emails::send_email(
Reader_Activation_Emails::EMAIL_TYPES['DELETE_ACCOUNT'],
$user->user_email,
[
[
'template' => '*DELETION_LINK*',
'value' => $url,
],
]
);

if ( $switched_locale ) {
\restore_previous_locale();
}

\wp_safe_redirect(
\add_query_arg(
[
Expand Down
Loading

0 comments on commit c121e5c

Please sign in to comment.