<?php
/**
 * Lgging user activity
 *
 * @category PHP
 * @package  VenoFileManager
 * @author   Nicola Franchini <info@veno.it>
 * @license  https://veno.es/shop/help Veno Commercial License
 * @link     http://filemanager.veno.it/
 */
use PHPMailer\PHPMailer\PHPMailer;

require_once dirname(__DIR__).'/assets/mail/vendor/autoload.php';

if (!class_exists('Logger', false)) {
    /**
     * Class Logger
     *
     * @category PHP
     * @package  VenoFileManager
     * @author   Nicola Franchini <info@veno.it>
     * @license  https://veno.es/shop/help Veno Commercial License
     * @link     http://filemanager.veno.it/
     */
    class Logger
    {
        /**
         * Print log file
         *
         * @param string $message the message to log
         * @param string $relpath relative path of log file // DROPPED in favor of dirname()
         *
         * @return $message
         */
        public static function log($message, $relpath = 'vfm-admin/')
        {
            global $setUp;
            if ($setUp->getConfig('log_file') == true) {
                $log_dir = dirname(__DIR__).'/_content/log/';
                $logjson = $log_dir.date('Y-m-d').'.json';

                // Creazione automatica .htaccess per protezione cartella log
                if (!file_exists($log_dir . '.htaccess')) {
                    $htaccess_content = "<Files \"*.json\">\n"
                        . "    <IfModule mod_authz_core.c>\n"
                        . "        Require all denied\n"
                        . "    </IfModule>\n"
                        . "    <IfModule !mod_authz_core.c>\n"
                        . "        Order Deny,Allow\n"
                        . "        Deny from all\n"
                        . "    </IfModule>\n"
                        . "</Files>";
                    
                    if (is_dir($log_dir) && is_writable($log_dir)) {
                        file_put_contents($log_dir . '.htaccess', $htaccess_content);
                    }
                }

                if (Utils::isFileWritable($logjson)) {
                    $message['time'] = date('H:i:s');
                    if (file_exists($logjson)) {
                        $oldlog = json_decode(file_get_contents($logjson), true);
                    } else {
                        $oldlog = array();
                    }

                    $daily = date('Y-m-d');
                    $oldlog[$daily][] = $message;
                    $f = fopen($logjson, 'a');
                    if (strtoupper(substr(PHP_OS, 0, 3)) === 'WIN') {
                        file_put_contents($logjson, json_encode($oldlog, JSON_FORCE_OBJECT));
                    } else {
                        if (flock($f, LOCK_EX | LOCK_NB)) {
                            file_put_contents($logjson, json_encode($oldlog, JSON_FORCE_OBJECT));
                            flock($f, LOCK_UN);
                        }
                    }
                    fclose($f);
                } else {
                    Utils::setError('The script does not have permissions to write inside "/_content/log/" folder. check CHMOD'.$logjson);
                    return;
                }
            }
        }

        /**
         * Log user login
         *
         * @return $message
         */
        public static function logAccess()
        {
            global $gateKeeper;
            global $setUp;
            $message = array(
                'user' => $gateKeeper->getUserInfo('name'),
                'action' => 'log_in',
                'type' => '',
                'item' => 'IP: '.Logger::getClientIP(),
            );
            Logger::log($message);
            if ($setUp->getConfig('notify_login')) {
                Logger::emailNotification('--', 'login');
            }
        }

        /**
         * Get user IP
         *
         * @return $ipaddress
         */
        public static function getClientIP()
        {
            if (!empty($_SERVER['HTTP_CLIENT_IP'])) {
                // check ip from share internet
                $ip = $_SERVER['HTTP_CLIENT_IP'];
            } elseif (!empty($_SERVER['HTTP_X_FORWARDED_FOR'])) {
                // check ip is pass from proxy
                $ip = $_SERVER['HTTP_X_FORWARDED_FOR'];
            } elseif (!empty($_SERVER['REMOTE_ADDR'])) {
                $ip = $_SERVER['REMOTE_ADDR'];
            } else {
                $ip = 'UNKNOWN';
            }
            return $ip;
        }

        /**
         * Log user creation of folders and files
         *
         * @param string $path  the path to set
         * @param string $isDir may be 'dir' or 'file'
         *
         * @return $message
         */
        public static function logCreation($path, $isDir)
        {
            global $gateKeeper;
            global $setUp;
            $path = addslashes($path);
            $message = array(
                'user' => $gateKeeper->getUserInfo('name'),
                'action' => 'ADD',
                'type' => $isDir ? 'folder':'file',
                'item' => ltrim($path, './'),
            );
            Logger::log($message);
            // Moved to /ajax/sendupnotif.php
            // if (!$isDir && $setUp->getConfig('notify_upload')) {
            //     Logger::emailNotification($path, 'upload');
            // }
            if ($isDir && $setUp->getConfig('notify_newfolder')) {
                Logger::emailNotification($path, 'newdir');
            }
        }

        /**
         * Log user deletion of folders and files
         *
         * @param string  $path   the path to set
         * @param boolean $isDir  file or directory
         * @param boolean $remote true if called inside vfm-admin
         *
         * @return $message
         */
        public static function logDeletion($path, $isDir, $remote = false)
        {
            global $gateKeeper;
            $path = addslashes($path);
            $message = array(
                'user' => $gateKeeper->getUserInfo('name'),
                'action' => 'REMOVE',
                'type' => $isDir ? 'folder':'file',
                'item' => ltrim($path, './'),
            );
            Logger::log($message);
        }
        
        /**
         * Log download of single files
         *
         * @param string $path     the path to set
         * @param bool   $folder   if is folder
         * @param string $relative relative path to /log/ folder
         *
         * @return $message
         */
        public static function logDownload($path, $folder = false, $relative = '')
        {
            global $gateKeeper;
            global $setUp;
            $user = $gateKeeper->getUserName();
            $mailmessage = '';
            $type = $folder ? 'folder' : 'file';
            if (is_array($path)) {
                foreach ($path as $value) {
                    $path = addslashes($value);
                    $message = array(
                        'user' => $user,
                        'action' => 'DOWNLOAD',
                        'type' => $type,
                        'item' => ltrim($path, './'),
                    );
                    $mailmessage .= $path."\n";
                    Logger::log($message, $relative);
                }
            } else {
                $path = addslashes($path);
                $message = array(
                    'user' => $user,
                    'action' => 'DOWNLOAD',
                    'type' => $type,
                    'item' => ltrim($path, './'),
                );
                $mailmessage = $path;
                Logger::log($message, $relative);
            }
            if ($setUp->getConfig('notify_download')) {
                Logger::emailNotification($mailmessage, 'download');
            }
        }

        /**
         * Log play of single track
         *
         * @param string $path the path to set
         *
         * @return $message
         */
        public static function logPlay($path)
        {
            global $gateKeeper;
            $path = addslashes($path);
            $message = array(
                'user' =>  $gateKeeper->getUserInfo('name') ? $gateKeeper->getUserInfo('name') : '--',
                'action' => 'PLAY',
                'type' => 'file',
                'item' => ltrim($path, './'),
            );
            Logger::log($message, '');
        }

        /**
         * Send email notfications for activity logs
         *
         * @param string $path   the path to set
         * @param string $action can be 'download' | 'upload' | 'newdir' | 'login' | 'newuser'
         * @param string $data   json_encoded additional message
         *
         * @return $message
         */
        public static function emailNotification($path = false, $action = false, $data = false)
        {
            global $setUp;
            global $gateKeeper;

            if (strlen($setUp->getConfig('upload_email')) > 5) {

                $time = $setUp->formatModTime(time());
                $message = $time."<br><br>";
                $alt_message = $time."\n\n";
                $message .= "IP : ".Logger::getClientIP()."<br>";
                $alt_message .= "IP : ".Logger::getClientIP()."\n";

                switch ($action) {
                case 'download':
                    $title = $setUp->getString('new_download');
                    break;
                case 'upload':
                    $title = $setUp->getString('new_upload');
                    break;
                case 'newdir':
                    $title = $setUp->getString('new_directory');
                    break;
                case 'login':
                    $title = $setUp->getString('new_access');
                    break;
                case 'newuser':
                    $title = $setUp->getString('new_user_has_been_created');
                    break;
                default:
                    $title = $setUp->getString('new_activity');
                    break;
                }

                $name = $gateKeeper->getUserInfo('name');

                if ($name) {
                    $message .= $setUp->getString('user')." : ".$name."<br>";
                    $alt_message .= $setUp->getString('user')." : ".$name."\n";
                }

                if ($path) {
                    $message .= $setUp->getString('path')." :<br>".nl2br($path)."<br>";
                    $alt_message .= $setUp->getString('path')." :\n".$path."\n";
                }

                if ($data) {
                    $get_data = json_decode($data);
                    $message .= nl2br($get_data);
                    $alt_message .= $get_data;
                }

                $sendTo = $setUp->getConfig('upload_email');

                Logger::sendMail(false, $sendTo, $title, $message, $alt_message);

                // OLD Method
                // mail(
                //     $sendTo,
                //     "=?UTF-8?B?".base64_encode($title)."?=",
                //     $message,
                //     "Content-type: text/plain; charset=UTF-8\r\n".
                //     "From: ".$from." <noreply@{$_SERVER['SERVER_NAME']}>\r\n".
                //     "Reply-To: ".$from." <noreply@{$_SERVER['SERVER_NAME']}>"
                // );
            }
        }

        /**
         * Send email notfications
         *
         * @param string $from       from
         * @param string $to         to
         * @param string $subject    subject
         * @param string $content    content
         * @param string $altmessage altmessage
         *
         * @return $message
         */
        public static function sendMail($from = false, $to = false, $subject = false, $content = false, $altmessage = false)
        {
            global $setUp;
            $mail = new PHPMailer();

            $mail->CharSet = 'UTF-8';
            $mail->setLanguage($setUp->lang);
            $appname = html_entity_decode($setUp->getConfig('appname'));

            if ($setUp->getConfig('smtp_enable')) {
                $mail->isSMTP();
                $mail->SMTPDebug = 0;
                // $mail->Debugoutput = 'html';

                $smtp_auth = $setUp->getConfig('smtp_auth');
                $mail->Host = $setUp->getConfig('smtp_server');
                $mail->Port = (int)$setUp->getConfig('port');

                $mail->SMTPOptions = array(
                    'ssl' => array(
                        'verify_peer' => false,
                        'verify_peer_name' => false,
                        'allow_self_signed' => true,
                    )
                );

                if ($setUp->getConfig('secure_conn') !== "none") {
                    $mail->SMTPSecure = $setUp->getConfig('secure_conn');
                }

                $mail->SMTPAuth = $smtp_auth;

                if ($smtp_auth == true) {
                    $mail->Username = $setUp->getConfig('email_login');
                    $mail->Password = $setUp->getConfig('email_pass');
                }
            }

            if (!$from) {
                $setfrom = $setUp->getConfig('email_from');
                if (!$setfrom) {
                    return $setUp->getString("setup_email_application");
                }
                $mail->setFrom($setfrom, $appname);
            } else {
                $mail->setFrom($from, '<'.$from.'>');
            }

            if (!$to) {
                return $setUp->getString("missing_recipient");
            }

            $mail->addAddress($to, '<'.$to.'>');

            if (!$subject) {
                return $setUp->getString("missing_subject");
            }

            $mail->Subject = html_entity_decode($subject);

            $email_logo = $setUp->getConfig('email_logo', false) ? dirname(__DIR__).'/_content/uploads/'.$setUp->getConfig('email_logo') : dirname(__DIR__).'/images/px.png';
            $mail->AddEmbeddedImage($email_logo, 'logoimg');

            // Retrieve the email template required
            $message = file_get_contents(Template::getMailTemplate('template-blank'));
            $app_url = $setUp->getConfig('script_url');

            // Replace the % with the actual information
            $message = str_replace('%app_url%', $app_url, $message);
            $message = str_replace('%app_name%', $appname, $message);
            $message = str_replace('%content%', $content, $message);

            $mail->msgHTML($message);
            $mail->AltBody = $altmessage;

            if (!$mail->send()) {
                return $mail->ErrorInfo;
            } else {
                return 'success';
            }
        }
    }
}
