<?php

namespace App\Controller\Auth;

use App\Controller\AppController;
use Cake\Event\Event;
use Cake\Mailer\MailerAwareTrait;
use Cake\I18n\I18n;
use Cake\Utility\Security;
use Cake\Utility\Text;

class UsersController extends AppController
{
    use MailerAwareTrait;

    public function initialize()
    {
        parent::initialize();
        $this->loadComponent('Captcha');
    }

    public function beforeFilter(Event $event)
    {
        parent::beforeFilter($event);
        $this->Auth->allow(['signup', 'logout', 'activateAccount', 'forgotPassword']);
        $this->viewBuilder()->layout('auth');

        if (isset($_COOKIE['lang']) && in_array($_COOKIE['lang'], get_site_languages(true))) {
            I18n::locale($_COOKIE['lang']);
        }
    }

    public function signin()
    {
        if ($this->Auth->user('id')) {
            return $this->redirect('/');
        }

        $user = $this->Users->newEntity();
        $this->set('user', $user);

        if ($this->request->is('post') || $this->request->query('provider')) {
            $user = $this->Auth->identify();
            if ($user) {
                $this->Auth->setUser($user);

                $_SESSION['Auth']['domains_auth'] = 'none';
                $multi_domains = get_all_multi_domains_list();
                $main_domain = get_option('main_domain', '');
                unset($multi_domains[$main_domain]);
                if (count($multi_domains)) {
                    $_SESSION['Auth']['User']['domains_auth'] = 'required';
                }

                if (version_compare(get_option('app_version', '1.0.0'), '2.0.0', '<')) {
                    $user['role'] = 2;
                    if ($user['account_type'] == 'Admin') {
                        $user['role'] = 1;
                    }
                }

                if ($user['role'] == 1) {
                    return $this->redirect([
                        'plugin' => false,
                        'controller' => 'Users',
                        'action' => 'dashboard',
                        'prefix' => 'admin'
                    ]);
                }
                return $this->redirect($this->Auth->redirectUrl());
            }
            $this->Flash->error(__('Invalid username or password, try again'));
        }
    }

    public function multidomainsAuth()
    {
        $this->autoRender = false;

        $this->response->type('gif');

        $this->response->body(base64_decode('R0lGODlhAQABAIAAAP///wAAACH5BAAAAAAALAAAAAABAAEAAAICRAEAOw=='));

        if (!$this->request->is('get')) {
            return $this->response;
        }

        try {
            if (isset($this->request->query['auth']) && !empty($this->request->query['auth'])) {
                $auth = data_decrypt($this->request->query['auth']);

                if ((time() - $auth['time']) > 60) {
                    return $this->response;
                }

                session_write_close();

                session_name($auth['session_name']);
                session_id($auth['session_id']);

                session_start();
            }
        } catch (\Exception $ex) {
        }
        return $this->response;
    }

    public function signup()
    {
        if ($this->Auth->user('id')) {
            return $this->redirect('/');
        }

        if ((bool)get_option('close_registration', false) ||
            (bool)get_option('private_service', false)) {
            return $this->redirect('/');
        }

        $user = $this->Users->newEntity();

        $this->set('user', $user);

        if ($this->request->is('post')) {
            if ((get_option('enable_captcha_signup') == 'yes') &&
                isset_captcha() &&
                !$this->Captcha->verify($this->request->data)
            ) {
                $this->Flash->error(__('The CAPTCHA was incorrect. Try again'));
                return null;
            }

            $user = $this->Users->patchEntity($user, $this->request->data);

            $user->api_token = Security::hash(Text::uuid(), 'sha1', true);
            $user->activation_key = Security::hash(Text::uuid(), 'sha1', true);

            $user->role = 2;
            $user->status = 1;
            $user->plan_id = 1;
            $user->first_name = $this->request->data['username'];
            $user->register_ip = get_ip();
            $user->redirect_type = get_option('member_default_redirect', 1);

            if (get_option('account_activate_email', 'yes') == 'yes') {
                $user->status = 2;
            }

            if ($this->Users->save($user)) {
                if (get_option('account_activate_email', 'yes') == 'yes') {
                    // Send activation email
                    $this->getMailer('User')->send('activation', [$user]);

                    $this->Flash->success(__("Your account has been created. " .
                        "Please check your email inbox or spam folder to activate your account."));
                    return $this->redirect(['action' => 'signin']);
                }
                $this->Flash->success(__('Your account has been created.'));
                return $this->redirect(['action' => 'signin']);
            }
            $this->Flash->error(__('Unable to add the user.'));
        }
        $this->set('user', $user);
    }

    public function logout()
    {
        return $this->redirect($this->Auth->logout());
    }

    public function activateAccount($username = null, $key = null)
    {
        if (!$username && !$key) {
            $this->Flash->error(__('Invalid Activation.'));
            return $this->redirect(['action' => 'signin']);
        }
        $user = $this->Users->find()
            ->contain(['Plans'])
            ->where([
                'Users.username' => $username,
                'Users.status' => 2,
                'Users.activation_key' => $key
            ])
            ->first();

        if (!$user) {
            $this->Flash->error(__('Invalid Activation.'));
            return $this->redirect(['action' => 'signin']);
        }

        $user->status = 1;
        $user->activation_key = '';

        if ($this->Users->save($user)) {
            $this->Flash->success(__('Your account has been activated.'));
            $this->Auth->setUser($user->toArray());
            return $this->redirect(['controller' => 'users', 'action' => 'dashboard', 'prefix' => 'member']);
        } else {
            $this->Flash->error(__('Unable to activate your account.'));
            return $this->redirect(['action' => 'signin', 'prefix' => 'auth']);
        }
    }

    public function forgotPassword($username = null, $key = null)
    {
        if ($this->Auth->user('id')) {
            return $this->redirect('/');
        }

        if (!$username && !$key) {
            $user = $this->Users->newEntity();
            $this->set('user', $user);

            if ($this->request->is(['post', 'put'])) {
                if ((get_option('enable_captcha_forgot_password') == 'yes') &&
                    isset_captcha() &&
                    !$this->Captcha->verify($this->request->data)
                ) {
                    $this->Flash->error(__('The CAPTCHA was incorrect. Try again'));
                    return null;
                }

                $user = $this->Users->findByEmail($this->request->data['email'])->first();

                if (!$user) {
                    $this->Flash->error(__('Invalid User.'));
                    return $this->redirect(['action' => 'forgotPassword', 'prefix' => 'auth']);
                }

                $user->activation_key = Security::hash(Text::uuid(), 'sha1', true);

                $user = $this->Users->patchEntity($user, $this->request->data, ['validate' => 'forgotPassword']);

                if ($this->Users->save($user)) {
                    // Send rest email
                    $this->getMailer('User')->send('forgotPassword', [$user]);

                    $this->Flash->success(__('Kindly check your email for reset password link.'));

                    return $this->redirect(['action' => 'forgotPassword', 'prefix' => 'auth']);
                } else {
                    $this->Flash->error(__('Unable to reset password.'));

                    return $this->redirect(['action' => 'forgotPassword', 'prefix' => 'auth']);
                }
            }
        } else {
            $user = $this->Users->find('all')
                ->where([
                    'username' => $username,
                    'status' => 1,
                    'activation_key' => $key
                ])
                ->first();
            if (!$user) {
                $this->Flash->error(__('Invalid Request.'));
                return $this->redirect(['action' => 'forgotPassword', 'prefix' => 'auth']);
            }

            if ($this->request->is(['post', 'put'])) {
                $user->activation_key = '';

                $user = $this->Users->patchEntity($user, $this->request->data, ['validate' => 'forgotPassword']);

                if ($this->Users->save($user)) {
                    $this->Flash->success(__('Your password has been changed.'));
                    return $this->redirect(['action' => 'signin', 'prefix' => 'auth']);
                } else {
                    $this->Flash->error(__('Unable to change your password.'));
                }
            }

            unset($user->password);

            $this->set('user', $user);
        }
    }
}
