Skip to content

Commit

Permalink
Use wp_mail_content_type filter to determine the Content Type when sa…
Browse files Browse the repository at this point in the history
…ving the logs
  • Loading branch information
donmhico committed Oct 8, 2024
1 parent 2263114 commit ccb6d3c
Show file tree
Hide file tree
Showing 3 changed files with 78 additions and 30 deletions.
30 changes: 1 addition & 29 deletions src/WPML_Email_Resender.php
Original file line number Diff line number Diff line change
Expand Up @@ -16,8 +16,6 @@ public function __construct($dispatcher) {
/**
* Resend mail
*
* @since {VERSION} Use the WP hook `wp_mail_content_type` as the resent mail `Content-Type` header.
*
* @param WPML_Mail $mail
*/
public function resendMail($mail) {
Expand All @@ -34,33 +32,7 @@ public function resendMail($mail) {
return WPML_Attachment::fromRelPath($attachments)->getPath();
}, $attachments);

$clean_headers = str_replace(
[
"\\r\\n",
"\r\n",
",\n",
",\\n"
],
"\n",
$mail->get_headers()
);

$headers = explode( "\n", $clean_headers );

for ( $ctr = 0; $ctr < count( $headers ); $ctr++ ) {
$header_arr = explode( ":", $headers[ $ctr ] );

if ( ! empty( $header_arr[0] ) && strtolower( $header_arr[0] ) === 'content-type' ) {
// Unset the content type header.
unset( $headers[ $ctr ] );
} else {
$headers[ $ctr ] = rtrim( $headers[ $ctr ], "," );
}
}

$headers[] = 'Content-Type: ' . apply_filters( 'wp_mail_content_type', 'text/html' );

$this->dispatcher->dispatch( $receivers, $mail->get_subject(), $mail->get_message(), $headers, $attachments );
$this->dispatcher->dispatch( $receivers, $mail->get_subject(), $mail->get_message(), WPML_Utils::clean_headers( $mail->get_headers() ), $attachments );
}

}
45 changes: 44 additions & 1 deletion src/WPML_Plugin.php
Original file line number Diff line number Diff line change
Expand Up @@ -500,7 +500,7 @@ public function log_email_failed( $wperror ) {
*
* @since 1.0
* @since 1.12.0 Short-circuit if $mailArray is not an array.
* @since {VERSION} Trim the subject to < 200 characters.
* @since {VERSION} Trim the subject to < 200 characters and save the Content-Type header if not set.
*
* @return array $mailOriginal
*/
Expand All @@ -525,6 +525,8 @@ public function log_email( $mailArray ) {
$mailArray['subject'] = mb_substr( $mailArray['subject'], 0, 195 ) . '...';
}

$mailArray['headers'] = $this->get_mail_headers( $mailArray );

$mail = (new WPML_MailExtractor())->extract($mailArray);
$mail->set_plugin_version($this->getVersionSaved());
$mail->set_timestamp(current_time( 'mysql' ));
Expand All @@ -535,6 +537,47 @@ public function log_email( $mailArray ) {
return $mailArray;
}

/**
* Get the headers of the mail to be logged.
*
* @since {VERSION}
*
* @param array $mail_array Array containing the mail data to be logged.
*
* @return string[]
*/
public function get_mail_headers( $mail_array ) {

$content_type = 'Content-Type: ' . apply_filters( 'wp_mail_content_type', 'text/html' );

if ( empty( $mail_array['headers'] ) ) {
return [ $content_type ];
}

$mail_headers = WPML_Utils::clean_headers( $mail_array['headers'] );

if ( empty( $mail_headers ) ) {
return [ $content_type ];
}

$should_force_add_content_type = true;

for ( $ctr = 0; $ctr < count( $mail_headers ); $ctr++ ) {
$header_arr = explode( ":", $mail_headers[ $ctr ] );

// If Content-Type header is already set, don't add it again.
if ( ! empty( $header_arr[0] ) && strtolower( $header_arr[0] ) === 'content-type' ) {
$should_force_add_content_type = false;
}
}

if ( $should_force_add_content_type ) {
$mail_headers[] = $content_type;
}

return $mail_headers;
}

public static function getClass() {
return __CLASS__;
}
Expand Down
33 changes: 33 additions & 0 deletions src/WPML_Utils.php
Original file line number Diff line number Diff line change
Expand Up @@ -292,4 +292,37 @@ public static function can_current_user_access_wp_mail_logging_submissions() {
return current_user_can( 'administrator' ) ||
current_user_can( WPML_Init::getInstance()->getService( 'plugin' )->getSetting( 'can-see-submission-data', 'manage_options' ) );
}

/**
* Clean the headers and return an array of headers.
*
* @since {VERSION}
*
* @param mixed $raw_headers Raw headers.
*
* @return string[]
*/
public static function clean_headers( $raw_headers ) {

if ( is_array( $raw_headers ) ) {
return $raw_headers;
}

$clean_headers = str_replace(
[
"\\r\\n",
"\r\n",
",\n",
",\\n"
],
"\n",
$raw_headers
);

$headers = explode( "\n", $clean_headers );

return array_filter( array_map( function( $header ) {
return rtrim( $header, "," );
}, $headers ) );
}
}

0 comments on commit ccb6d3c

Please sign in to comment.