<?php
namespace services\authorization;

use \models\User;
use PHPMailer\PHPMailer\PHPMailer;
use PHPMailer\PHPMailer\Exception;

/**
 * Password reset link service
 * @author Jérôme Brilland
 * @version 2.1
 * @copyright (c) 2019-2023, Jérôme Brilland
 * @license http://www.gnu.org/licenses/gpl.txt GNU General Public License
 */
class SendResetLinkEmail {

    private $email;

    public function __construct( $email ) {
        $this->email = $email;
    }

    public function perform( $listener ) {
        $i18n = \IoC::resolve( 'i18n' );
        $user = User::findByEmail( $this->email );
        if ( empty( $user ) ) {
            $listener->sendResetLinkEmailFailed( $i18n->__( 'email_address_not_found' ) );
        } else {
            $token = bin2hex( random_bytes ( 32 ) );
            $user->password_reset_token = $token;
            $user->password_reset_sent_at = date( 'Y-m-d H:i:s' );
            $user->save();
            try {
                $this->sendEmail( $user );
            } catch( \Exception $e ) {
                \IoC::resolve( 'logger' )->write( sprintf( '[%s] [%s] [%s] %s', date( 'Y-m-d H:i:s' ), __FILE__, 'debug', $e->getMessage() ) );
                $listener->sendResetLinkEmailFailed( $i18n->__( 'an_error_occurred' ) );
                return;
            }
            $listener->sendResetLinkEmailSucceeded( $i18n->__( 'email_sent_password_reset' ) );
        }
    }

    private function sendEmail( $user ) {
        $i18n = \IoC::resolve( 'i18n' );
	    $mail = new PHPMailer( true );
        $settings = \IoC::resolve( 'settings' );
        
        $mail->setFrom( $settings['from_email'], $settings['from_name'] );
        $mail->addAddress( $user->email );
 
        $mail->Subject = $i18n->__( 'password_reset' );
        $link = BASE_URL . 'password/reset/' . $user->password_reset_token;
        $mail->isHTML( true );

        $latte = new \Latte\Engine();
        $latte->setLoader( new \Latte\Loaders\FileLoader( APP_DIR . TEMPLATES_DIR . 'passwordreset' ) );
        \IoC::resolve( 'eventmediator' )->trigger( 'before_load_reset_link_email_template', [$latte, $user] );

        $mail->Body = $latte->renderToString( 'password_reset.html', ['link' => $link] );
        $mail->AltBody = $latte->renderToString( 'password_reset.txt', ['link' => $link] );

        \IoC::resolve( 'eventmediator' )->trigger( 'before_send_email', [$mail] );
        $mail->Send();
    }
}
