<?php
/**
* Plugin Name: App config
* Description: App configuration must use functions
* - Add SVG to mime_types.
* - Clean file name when uploading files in WordPress.
* - Disable Login errors.
* - Add Security headers.
* - Add s3 uploads custom endpoint (S3_UPLOADS_ENDPOINT)
* - Remove WordPress version from HTML source.
* - WP error log to stdout (ERROR_LOG_TO_STDOUT)
* - Setup PHPMailer with SMTP (SMTP_SERVER, SMTP_PORT, SMTP_LOGIN, SMTP_PASSWORD and SMTP_SECURE)
* Version: 202309-01
* Author: felegy
* Author URI: https://github.com/felegy
*/

namespace App;

defined('ABSPATH') || die('Restricted Area');

class AppMuPlugin
{
    public function __construct()
    {
        // Define constants
        $this->defineConstants();

        if (defined('ERROR_LOG_TO_STDOUT')) {
            if (ERROR_LOG_TO_STDOUT) {
                // WP error log to stdout
                $this->errorLogToStdout();
            }
        }
        if (defined('S3_UPLOADS_ENDPOINT')) {
            // Filter S3 Uploads params.
            $this->s3UploadsEndpoint();
        }

        if (defined('SMTP_ENABLED') && SMTP_ENABLED) {
            // If SMTP is enabled, setup PHPMailer
            if (defined('SMTP_SERVER') && defined('SMTP_PORT')) {
                $this->setupPhpMailer();
            }
        }

        $this->headerSecurity();
        $this->noWordpressErrors();
        $this->sanitizeFileName();
        $this->removeWpVersion();
        $this->ccMimeTypes();
        $this->twoFactorDefault();
        $this->onLogoutRedirect();
    }


    private function defineConstants()
    {

        if (!defined('SMTP_SERVER')) {
            define('SMTP_SERVER', '127.0.0.1');
        }

        if (!defined('SMTP_PORT')) {
            define('SMTP_PORT', 1025);
        }

        if (!defined('BLOG_SLUG')) {
            define('BLOG_SLUG', 'wp');
        }
    }

    private function errorLogToStdout()
    {
        // Add your initialization code here.
        // WP error log to stdout
        add_action('init', function () {
            ini_set ('error_log', '/dev/stdout'); // phpcs:ignore
        }, 10);
    }

    private function s3UploadsEndpoint()
    {
        // Filter S3 Uploads params.
        add_filter('s3_uploads_s3_client_params', function ($params) {
            $params['endpoint'] = defined('S3_UPLOADS_ENDPOINT') ? S3_UPLOADS_ENDPOINT : "";
            $params['use_path_style_endpoint'] = true;
            $params['debug'] = false; // Set to true if uploads are failing.
            return $params;
        });
    }

    private function headerSecurity()
    {
        // Add Security headers.
        add_filter(
            'wp_headers',
            function ($headers) {
                $headers['X-Frame-Options'] = 'SAMEORIGIN';
                $headers['X-Content-Type-Options'] = 'nosniff';
                $headers['X-XSS-Protection'] = '1; mode=block';
                $headers['Strict-Transport-Security'] = 'max-age=31536000; includeSubDomains';
                $headers['Referrer-Policy'] = 'same-origin';
                $headers['Permissions-Policy'] = 'geolocation=()';
                $headers['Content-Security-Policy'] = 'upgrade-insecure-requests';

                return $headers;
            }
        );
    }

    private function noWordpressErrors()
    {
        add_filter('login_errors', function () {
            return 'Hiba történt a belépés során!';
        });
    }

    private function sanitizeFileName()
    {
        // Clean file name when uploading files in WordPress.
        add_filter('sanitize_file_name', function ($filename) {
            $extension = substr($filename, strrpos($filename, '.') + 1);
            $filename  = substr($filename, 0, strrpos($filename, '.'));

            return sanitize_title($filename) . '.' . $extension;
        });
    }

    private function removeWpVersion()
    {
        // Remove WordPress version from HTML source.
        add_filter('the_generator', '__return_empty_string');
    }

    private function ccMimeTypes()
    {
        // Add SVG to mime_types.
        add_filter('upload_mimes', function ($mimes) {
            $mimes['svg'] = 'image/svg+xml';
            return $mimes;
        });
    }

    private function setupPhpMailer()
    {
        add_action('phpmailer_init', function ($phpmailer) {
            $phpmailer->Host = SMTP_SERVER;
            $phpmailer->Port = SMTP_PORT;

            // If SMTP_LOGIN is defined, use it for authentication
            if (defined('SMTP_LOGIN')) {
                $phpmailer->SMTPAuth = true; // Enable SMTP authentication
                $phpmailer->Username = SMTP_LOGIN; // Set the SMTP username
                $phpmailer->Password = defined('SMTP_PASSWORD') ? SMTP_PASSWORD : '';
            } else {
                $phpmailer->SMTPAuth = false; // Disable SMTP authentication
            }

            if (defined('SMTP_DEBUG') && SMTP_DEBUG) {
                $phpmailer->SMTPDebug = 2; // Enable verbose debug output
            } else {
                $phpmailer->SMTPDebug = 0; // Disable debug output
            }

            if (defined('SMTP_SECURE') && SMTP_SECURE) {
                $phpmailer->SMTPSecure = SMTP_SECURE; // Set the encryption type
            } else {
                $phpmailer->SMTPSecure = false; // Disable encryption
            }

            if (defined('SMTP_DOMAIN')) {
                $phpmailer->From = BLOG_SLUG . '@' . SMTP_DOMAIN;
            } else {
                $dsn = (object) parse_url(get_bloginfo('url'));
                $phpmailer->From = BLOG_SLUG . '@' . $dsn->host;
            }

            $phpmailer->FromName = get_bloginfo('name');

            $phpmailer->isSMTP();
        });
    }

    private function twoFactorDefault()
    {
        add_filter('two_factor_providers', function ($providers) {
            // Disable FIDO U2F by default
            // ISSUE https://wordpress.org/support/topic/i-cant-add-my-yubikey/
            $providers['Two_Factor_FIDO_U2F'] = '';
            // Disable Dummy provider by default
            $providers['Two_Factor_Dummy'] = '';
            return $providers;
        });

        // Enable Two Factor Email by default
        //  force email two factor authentication
        add_filter('two_factor_enabled_providers_for_user', function ($providers) {
            if (! in_array('Two_Factor_Email', $providers)) {
                array_push($providers, 'Two_Factor_Email');
            }
            return $providers;
        });
    }

    private function onLogoutRedirect()
    {
        add_action('wp_logout', function () {
            if (defined('LOGOUT_REDIRECT_URL')) {
                wp_redirect(LOGOUT_REDIRECT_URL);
                exit;
            }
        });
    }
}

new AppMuPlugin();
