<?php

class CrmController extends BaseController {

	/**
	 * Constructor
	 */
	public function __construct() {
		// Establish Filters
		if (Sentry::check()) {
			$user = User::find(Sentry::getUser()->id);
			if ($user && !$user->hasAnyRole(array(Role::ROLE_CRM, Role::ROLE_LOGISTICS, Role::ROLE_FRANCHISEES, Role::ROLE_AGENT, Role::ROLE_SIZER))) {
				$this->beforeFilter('hasRole:' . Role::ROLE_CRM, array('except' => 'getRefrenceStat'));
				$this->beforeFilter('hasRole:' . Role::ROLE_LOGISTICS, array('except' => 'getRefrenceStat'));
				$this->beforeFilter('hasRole:' . Role::ROLE_FRANCHISEES, array('except' => 'getRefrenceStat'));
				$this->beforeFilter('hasRole:' . Role::ROLE_AGENT, array('except' => 'getRefrenceStat'));
				$this->beforeFilter('hasRole:' . Role::ROLE_SIZER, array('onli' => 'needSize'));
			}
		}
		else {
			$this->beforeFilter('auth');
		}
	}

	protected function getPartners($input = false, $all = false) {
		$limit = 50;
		if ($all) {
			$limit = 10000;
		}
		if ($input) {
			$orderBy = 'salenextdatetime';
			if (isset($input['statusType']) && $input['statusType'] == 'agreed') {
				$orderBy = 'datetime_of_agree';
			}
			if (isset($input['searchText'])) {
				$searchText = $input['searchText'];
				if ($searchText) {
					$searchText	 = e($searchText);
					$where			 = '(name LIKE "%' . $searchText . '%" OR phone LIKE "%' . $searchText . '%" OR city LIKE "%' . $searchText . '%" OR address LIKE "%' . $searchText . '%" OR email LIKE "%' . $searchText . '%" OR comment LIKE "%' . $searchText . '%" OR leads.data LIKE "%\":' . $searchText . '%")';
					$partners		 = Partner::with('user', 'lead')
									->leftJoin('leads', function($join) {
										$join->on('leads.id', '=', 'partners.lead_id');
									})
									->my($input)
									->whereRaw($where)
									->checkStatus($input)
									->orderBy('salenextdatetime', 'ASC')
									->paginate($limit);
				}
				else {
					$partners = Partner::with('user')->my($input)->checkStatus($input)->orderBy($orderBy, 'ASC')->paginate($limit);
				}
			}
			else {
				$partners = Partner::with('user')->my($input)->checkStatus($input)->orderBy($orderBy, 'ASC')->paginate($limit);
			}
		}
		else {
			$partners = Partner::with('user')->my($input)->checkStatus($input)->orderBy($orderBy, 'ASC')->paginate($limit);
		}

		return $partners;
	}

	public function index() {
		$user = User::find(Sentry::getUser()->id);

		$input = Input::except('page');

		if (!Input::has('searchText')) {
			$input['searchText'] = '';
		}
		if (!Input::has('statusType')) {
			$input['statusType'] = Session::get('crm_statusType');
		}
		if (!Input::has('status')) {
			$input['status'] = Session::get('crm_status');
		}
		if (!Input::has('rejectId')) {
			$input['rejectId'] = Session::get('crm_rejectId');
		}
		if (!Input::has('type')) {
			$input['type'] = Session::get('crm_type');
		}
		if (!Input::has('date')) {
			$input['date'] = Session::get('crm_date');
		}
		if (!Input::has('user_id')) {
			$input['user_id'] = Session::get('crm_user_id');
		}
		if (!$input['statusType']) {
			$input['statusType'] = 'work';
		}
		if (User::find(Sentry::getUser()->id)->hasRole(Role::ROLE_LOGISTICS) && !User::find(Sentry::getUser()->id)->hasRole(Role::ROLE_CRM) && !Sentry::getUser()->inGroup(Sentry::findGroupByName('Admins'))) {
			if (!isset($input['statusType']) || !in_array($input['statusType'], array('checkpatterns', 'agreed', 'agreedfranchisees', 'paywaiting', 'production'))) {
				$input['statusType'] = 'agreed';
			}
		}
		if (User::find(Sentry::getUser()->id)->hasRole(Role::ROLE_LOGISTICS)) {
			if (isset($input['statusType']) && ($input['statusType'] == 'agreed' || $input['statusType'] == 'agreedfranchisees') && (!isset($input['type']) || !$input['type'])) {
				$input['type'] = 'registration';
			}
			if (isset($input['statusType']) && ($input['statusType'] == 'production') && (!isset($input['type']) || !$input['type'])) {
				$input['type'] = 'sizing';
			}
		}
		if (User::find(Sentry::getUser()->id)->hasRole(Role::ROLE_FRANCHISEES)) {
			if (isset($input['statusType']) && ($input['statusType'] == 'agreedfranchisees') && (!isset($input['type']) || !$input['type'])) {
				$input['type'] = 'commondelivery';
			}
		}
		if (User::find(Sentry::getUser()->id)->hasRole(Role::ROLE_AGENT)) {
			if (isset($input['statusType']) && ($input['statusType'] == 'agreedagent') && (!isset($input['type']) || !$input['type'])) {
				$input['type'] = 'delivery';
			}
		}

		if (Input::has('statusType') && $input['statusType'] == 'agreed' && $input['type'] != 'success') {
			$partners = $this->getPartners($input, true);
		}
		else {
			$partners = $this->getPartners($input);
		}
		$dates = null;
		if (Input::has('statusType') && $input['statusType'] == 'agreed' && $input['type'] != 'success') {
			foreach ($partners as $partner) {
				$datetime						 = explode(' ', $partner->datetime_of_agree);
				$date								 = explode('-', $datetime[0]);
				$dates[$datetime[0]] = "{$date[2]} {$this->months[$date[1]]}";
				if (!isset($input['date']) || $input['date'] == '') {
					$input['date'] = $datetime[0];
				}
				if ($input['date'] != $datetime[0]) {
					$partner->hide = 1;
				}
			}
		}
		$franchiseesList = null;
		if (Input::has('statusType') && $input['statusType'] == 'agreedfranchisees' && $input['type'] == 'registration') {
			foreach (User::with('roles')->get() as $user) {
				if ($user->hasRole(Role::ROLE_FRANCHISEES) && !$user->hasAccess('admin')) {
					$franchiseesList [] = $user->toArray();
				}
			}
		}

		$partners = $this->getPartners($input);

		Session::put('crm_statusType', $input['statusType']);
		Session::put('crm_status', $input['status']);
		Session::put('crm_rejectId', $input['rejectId']);
		Session::put('crm_type', $input['type']);
		Session::put('crm_date', $input['date']);
		Session::put('crm_user_id', $input['user_id']);

		$myClientCount	 = 0;
		$allClientCount	 = 0;
		if (!Sentry::getUser()->hasAccess('admin') && User::find(Sentry::getUser()->id)->hasRole(Role::ROLE_CRM)) {
			$myClientCount	 = Partner::my(array('statusType' => 'work'))->checkStatus(array('statusType' => 'work'))->whereRaw(DB::raw('salenextdatetime < NOW()'))->count();
			$allClientCount	 = Partner::where('user_id', '!=', Sentry::getUser()->id)->whereRaw('user_id NOT IN (SELECT user_id FROM users_roles WHERE role_id=10)')->checkStatus(array('statusType' => 'work'))->where('status', '!=', Partner::STATUS_WAIT_CLIENT_PAY)->whereRaw(DB::raw('salenextdatetime < NOW()'))->count();
		}

		return View::make('crm.index')
										->with('user', $user)
										->with('input', $input)
										->with('partners', $partners)
										->with('dates', $dates)
										->with('franchiseesList', $franchiseesList)
										->with('months', $this->months)
										->with('myClientCount', $myClientCount)
										->with('allClientCount', $allClientCount);
	}

	//Список машин на снятие размеров
	public function needSize() {
		return View::make('crm.needsize')
										->with('partners', Partner::whereStatus(Partner::STATUS_SIZING)->orderBy('need_size_message', 'ASC')->get())
										->with('months', $this->months);
	}

	//аякс поиск
	public function search() {
		$user	 = User::find(Sentry::getUser()->id);
		$input = Input::except('page');

		if (!Input::has('statusType')) {
			$input['statusType'] = 'work';
		}
		if (User::find(Sentry::getUser()->id)->hasRole(Role::ROLE_LOGISTICS) && !User::find(Sentry::getUser()->id)->hasRole(Role::ROLE_CRM) && !Sentry::getUser()->inGroup(Sentry::findGroupByName('Admins'))) {
			if (!Input::has('statusType') || !in_array($input['statusType'], array('checkpatterns', 'agreed', 'agreedfranchisees', 'paywaiting', 'production'))) {
				$input['statusType'] = 'agreed';
			}
		}
		if (User::find(Sentry::getUser()->id)->hasRole(Role::ROLE_LOGISTICS)) {
			if (isset($input['statusType']) && ($input['statusType'] == 'agreed' || $input['statusType'] == 'agreedfranchisees') && (!isset($input['type']) || !$input['type'])) {
				$input['type'] = 'registration';
			}
			if (isset($input['statusType']) && ($input['statusType'] == 'production') && (!isset($input['type']) || !$input['type'])) {
				$input['type'] = 'sizing';
			}
		}
		if (User::find(Sentry::getUser()->id)->hasRole(Role::ROLE_FRANCHISEES)) {
			if (isset($input['statusType']) && ($input['statusType'] == 'agreedfranchisees') && (!isset($input['type']) || !$input['type'])) {
				$input['type'] = 'commondelivery';
			}
		}
		if (User::find(Sentry::getUser()->id)->hasRole(Role::ROLE_AGENT)) {
			if (isset($input['statusType']) && ($input['statusType'] == 'agreedagent') && (!isset($input['type']) || !$input['type'])) {
				$input['type'] = 'delivery';
			}
		}

		if (Input::has('statusType') && $input['statusType'] == 'agreed' && $input['type'] != 'success') {
			$partners = $this->getPartners($input, true);
		}
		else {
			$partners = $this->getPartners($input);
		}
		$dates = null;
		if (Input::has('statusType') && $input['statusType'] == 'agreed' && $input['type'] != 'success') {
			foreach ($partners as $partner) {
				$datetime						 = explode(' ', $partner->datetime_of_agree);
				$date								 = explode('-', $datetime[0]);
				$dates[$datetime[0]] = "{$date[2]} {$this->months[$date[1]]}";
				if (!isset($input['date']) || $input['date'] == '') {
					$input['date'] = $datetime[0];
				}
				if ($input['date'] != $datetime[0]) {
					$partner->hide = 1;
				}
			}
		}
		$franchiseesList = null;
		if (Input::has('statusType') && $input['statusType'] == 'agreedfranchisees' && $input['type'] == 'registration') {
			foreach (User::with('roles')->get() as $user) {
				if ($user->hasRole(Role::ROLE_FRANCHISEES) && !$user->hasAccess('admin')) {
					$franchiseesList [] = $user->toArray();
				}
			}
		}

		Session::put('crm_statusType', $input['statusType']);
		if( isset($input['rejectId']) ){
		  Session::put('crm_rejectId', $input['rejectId']);
		}
		if( isset($input['status']) ){
			Session::put('crm_status', $input['status']);
		}
		if( isset($input['type']) ){
			Session::put('crm_type', $input['type']);
		}
		if( isset($input['date']) ){
			Session::put('crm_date', $input['date']);
		}
		if( isset($input['user_id']) ){
			Session::put('crm_user_id', $input['user_id']);
		}

		$response = array(
				'status'	 => 'success',
				'htmlText' => View::make('crm.table')
								->with('user', $user)
								->with('input', $input)
								->with('partners', $partners)
								->with('dates', $dates)
								->with('franchiseesList', $franchiseesList)
								->with('months', $this->months)
								->render()
		);

		return Response::json($response);
	}

	public function searchPage() {
		$input = Input::all();

		$searchText = $input['searchLine'];

		$where = 'partners.id=' . intval($searchText) . ' OR partners.name LIKE "%' . $searchText . '%" OR partners.phone LIKE "%' . $searchText . '%" OR partners.city LIKE "%' . $searchText . '%" OR partners.address LIKE "%' . $searchText . '%" OR partners.email LIKE "%' . $searchText . '%" OR partners.comment LIKE "%' . $searchText . '%" OR leads.data LIKE "%:' . $searchText . '%" OR partners.cart LIKE "%' . $searchText . '%"';

		$firstSymbol = substr($input['searchLine'], 0, 1);
		if ($firstSymbol == '8') {
			$where .= ' OR partners.phone LIKE "%' . substr($input['searchLine'], 1) . '%"';
		}
		if (User::find(Sentry::getUser()->id)->hasAnyRole(array(Role::ROLE_FRANCHISEES, Role::ROLE_AGENT))) {
			$partners = Partner::with('lead')->my()
							->whereRaw("({$where})")
							->leftJoin('leads', function($join) {
								$join->on('leads.id', '=', 'partners.lead_id');
							})
							->select('partners.*')
							->get();
		}
		else {
			$partners = Partner::with('lead')
							->whereRaw("({$where})")
							->leftJoin('leads', function($join) {
								$join->on('leads.id', '=', 'partners.lead_id');
							})
							->select('partners.*')
							->get();
		}
    $count = $partners->count();
		return $this->setupLayout('crm.search')
										->with('input', $input)
						        ->with('count', $count)
										->with('partners', $partners);
	}

	//аякс глобальный поиск
	public function globalSearch() {
		$input = Input::all();

		$searchText = $input['searchLine'];

		$where = 'partners.id=' . intval($searchText) . ' OR partners.name LIKE "%' . $searchText . '%" OR partners.phone LIKE "%' . $searchText . '%" OR partners.city LIKE "%' . $searchText . '%" OR partners.address LIKE "%' . $searchText . '%" OR partners.email LIKE "%' . $searchText . '%" OR partners.comment LIKE "%' . $searchText . '%" OR leads.data LIKE "%\":' . $searchText . '%"';

		$firstSymbol = substr($input['searchLine'], 0, 1);
		if ($firstSymbol == '8') {
			$where .= ' OR partners.phone LIKE "%' . substr($input['searchLine'], 1) . '%"';
		}
		if (User::find(Sentry::getUser()->id)->hasAnyRole(array(Role::ROLE_FRANCHISEES, Role::ROLE_AGENT))) {
			$partners = Partner::with('lead')->my()
							->leftJoin('leads', function($join) {
								$join->on('leads.id', '=', 'partners.lead_id');
							})
							->whereRaw("({$where})")
							->limit(10)
							->get(array(DB::raw('partners.*')));
		}
		else {
			$partners = Partner::with('lead')
							->leftJoin('leads', function($join) {
								$join->on('leads.id', '=', 'partners.lead_id');
							})
							->whereRaw("({$where})")
							->limit(10)
							->get(array(DB::raw('partners.*')));
		}

		$response = array();
		foreach ($partners as &$partner) {
			$value							 = $partner->toArray();
			$value['statusName'] = $partner->getRawStatusName();
			$response []				 = $value;
		}

		return Response::json($response);
	}

	//аякс запрос информации по определенном клиенте
	public function getPartner($id) {
		$partner = Partner::find($id);
		if ($partner == null || !is_numeric($id)) {
			$response = array(
					'status' => 'fail'
			);
		}
		else {
			$response = array(
					'status'	 => 'success',
					'partner'	 => $partner->toArray()
			);
		}

		return Response::json($response);
	}

	//аякс сохранение информации о партнере
	public function updatePartner() {
		$input = Input::all();
		$id		 = $input['partner_edit_id'];

		if (Session::token() !== Input::get('_token')) {
			$response = array(
					'status' => 'fail'
			);
			return Response::json($response);
		}

		$validator = Validator::make($input, array(
								'partner_edit_name'	  => 'required',
								'partner_edit_phone'  => 'required_without:partner_edit_email',
								'partner_edit_email'  => 'email',
				        'partner_edit_source' => 'required',
				        'partner_new_source'  => 'sometimes|required'
		));
		
		if ($validator->fails()) {
			$messages = $validator->messages();
			if ($messages->has('partner_edit_name')) {
				$message		 = 'Необходимо указать имя';
				$error_field = 'partner_edit_name';
			}
			elseif ($messages->has('partner_edit_phone')) {
				$message		 = 'Необходимо указать телефон';
				$error_field = 'partner_edit_phone';
			}
			elseif ($messages->has('partner_edit_email')) {
				$message		 = 'Неверный формат e-mail адреса';
				$error_field = 'partner_edit_email';
			}
			elseif ($messages->has('partner_edit_source')) {
				$message		 = 'Необходимо указать источник информации';
				$error_field = 'partner_edit_source';
			}
			elseif ($messages->has('partner_new_source')) {
				$message		 = 'Необходимо указать новый источник информации';
				$error_field = 'partner_new_source';
			}
			$response = array(
					'status'				 => 'fail',
					'error_message'	 => $message,
					'error_field'		 => $error_field
			);
			return Response::json($response);
		}

		if (User::find(Sentry::getUser()->id)->hasRole(Role::ROLE_AGENT) && !User::find(Sentry::getUser()->id)->hasAccess('admin')) {
			$site = Site::find(23);
			Lead::create(array(
					"site_id"		 => 23,
					"project_id" => $site->project_id,
					"entrypoint" => "Заказ от агента",
					"name"			 => trim($input['partner_edit_name']),
					"phone"			 => $this->preparePhone($input['partner_edit_phone']),
					"email"			 => $input['partner_edit_email'],
					"data"			 => json_encode('{"примечание":"' . e($input['partner_edit_info']) . '"}'),
					"agent_id"	 => Sentry::getUser()->id,
			));

			$response = array(
					'status' => 'success'
			);
		}
		else {
			if ($id) {
				$partner = Partner::find($id);
				if ($partner == null) {
					return \App::abort(404);
				}
				$partner->name		       = e(trim($input['partner_edit_name']));
				$partner->phone		       = e($this->preparePhone($input['partner_edit_phone']));
				$partner->email		       = e($input['partner_edit_email']);
				//$partner->info_source_id = e($input['partner_edit_source']);
				$partner->comment	       = e($input['partner_edit_info']);
				$partner->save();
			}
			else {
				$sourceId = 0;
				if( isset($input['partner_new_source']) ){
					// создание нового источника информации
					$infoSource = InfoSource::create(array(
										'project_id'			 => e($input['partner_edit_project_id']),
										'source'					 => e($input['partner_new_source'])
					));

					$sourceId = $infoSource->id;
				}
				else{
					$sourceId = e($input['partner_edit_source']);
				}

				$partner = Partner::create(array(
										'project_id'			 => e($input['partner_edit_project_id']),
										'user_id'					 => Sentry::getUser()->id,
										'status'					 => Partner::STATUS_WORK,
										'name'						 => e(trim($input['partner_edit_name'])),
										'phone'						 => e($this->preparePhone($input['partner_edit_phone'])),
										'email'						 => e($input['partner_edit_email']),
						        'info_source_id'	 => $sourceId,
										'comment'					 => e($input['partner_edit_info']),
										'salenextdatetime' => DB::raw('DATE_ADD(NOW(), INTERVAL 30 MINUTE)')
				));

				$refrence = Refrence::create(array(
										'partner_id'			 => e($partner->id),
										'comment'					 => e("Добавлен в клиенты"),
										'status'					 => e(Partner::STATUS_WORK),
										'sender_user_id'	 => e(Sentry::getUser()->id),
										'reciver_user_id'	 => e(Sentry::getUser()->id)
				));
			}

			$response = array(
					'status'	 => 'success',
					'partner'	 => $partner->toArray()
			);
		}

		return Response::json($response);
	}

	//берем клиента с которым надо сейчас связаться
	public function getRefrence() {
		$partners	 = Partner::my()->checkStatus(Input::all())->where('salenextdatetime', '<', DB::raw('NOW()'))->orderBy('salenextdatetime', 'ASC')->take(1)->get();
		$partners	 = $partners->toArray();
		$partner	 = false;
		if ($partners) {
			$partner = array_shift($partners);
		}

		$response = array(
				'status'	 => 'success',
				'partner'	 => $partner
		);

		return Response::json($response);
	}

	//берем статистику по заявкам и клиентам с которыми надо работать
	public function getRefrenceStat() {
		$user			 = User::find(Sentry::getUser()->id);
		$dateWhere = '(salenextdatetime<NOW())';

		$leadsCnt		 = 0;
		$partnersCnt = 0;
		if (!Sentry::getUser()->inGroup(Sentry::findGroupByName('Admins'))) {
			if ($user->hasRole(Role::ROLE_LEADS)) {
				$leadsCnt = Lead::inMyProjects()->count();
			}
			if ($user->hasRole(Role::ROLE_CRM) && !$user->hasRole(Role::ROLE_LOGISTICS)) {
				$partnersCnt = Partner::with('user')->my()->checkStatus()->whereRaw($dateWhere)->count();
			}
			elseif (!$user->hasRole(Role::ROLE_CRM) && $user->hasRole(Role::ROLE_LOGISTICS)) {
				$partnersCnt = Partner::with('user')->my()->checkStatus()->whereRaw($dateWhere)->count();
				$partnersCnt += Partner::with('user')->my(array('statusType' => 'agreedfranchiseesinwork'))->checkStatus(array('statusType' => 'agreedfranchiseesinwork'))->whereRaw($dateWhere)->count();
			}
			elseif ($user->hasRole(Role::ROLE_CRM) && $user->hasRole(Role::ROLE_LOGISTICS)) {
				$partnersCnt = Partner::with('user')->my()->whereIn('status', array(Partner::STATUS_WORK, Partner::STATUS_WAIT_CLIENT_PAY, Partner::STATUS_REGISTRATION))->whereRaw($dateWhere)->count();
			}
			elseif ($user->hasRole(Role::ROLE_FRANCHISEES)) {
				$partnersCnt = Partner::with('user')->my()->whereStatus(Partner::STATUS_WORK)->whereRaw($dateWhere)->count();
			}
		}

		$response = array(
				'status'			 => 'success',
				'partnersCnt'	 => $partnersCnt,
				'leadsCnt'		 => $leadsCnt
		);

		return Response::json($response);
	}

	//откладываем на 15 минут
	public function holdRefrence() {
		$input = Input::all();
		$id		 = $input['partner_id'];

		if (!$id || !is_numeric($id)) {
			$response = array(
					'status'	 => 'fail',
					'message'	 => 'Нет id клиента'
			);
			return Response::json($response);
		}
		$partner = Partner::find($id);

		if ($partner == null || !is_numeric($id) || $partner->user_id != Sentry::getUser()->id) {
			$response = array(
					'status'	 => 'fail',
					'message'	 => 'Клиент не найден'
			);
			return Response::json($response);
		}
		$partner->salenextdatetime = DB::raw('DATE_ADD(NOW(), INTERVAL 15 MINUTE)');
		$partner->save();

		$response = array(
				'status' => 'success'
		);

		return Response::json($response);
	}

	//аякс получение комментариев
	public function getPartnerComments($partnerId) {
		$partner = Partner::find($partnerId);
		if ($partner == null || !is_numeric($partnerId)) {
			$response = array(
					'status' => 'fail'
			);
		}
		else {
			$comments = $partner->getComments(0);

			$partner						 = $partner->toArray();
			$partner['comments'] = $comments->toArray();
			if (is_array($partner['comments'])) {
				foreach ($partner['comments'] as &$comment) {
					$comment['comment'] = nl2br($comment['comment']);
				}
			}

			$response = array(
					'status'	 => 'success',
					'partner'	 => $partner
			);
		}

		return Response::json($response);
	}

	//аякс получение нового клиента, для работы
	public function getWorkPartner() {
		$this->user		 = Auth::user();
		$myClientCount = Partner::my(array('statusType' => 'work'))->checkStatus(array('statusType' => 'work'))->whereRaw(DB::raw('salenextdatetime < NOW()'))->count();

		if (!$myClientCount) {
			$partner									 = Partner::where('user_id', '!=', Sentry::getUser()->id)->whereRaw('user_id NOT IN (SELECT user_id FROM users_roles WHERE role_id=10)')->checkStatus(array('statusType' => 'work'))->where('status', '!=', Partner::STATUS_WAIT_CLIENT_PAY)->whereRaw(DB::raw('salenextdatetime < NOW()'))->orderBy('salenextdatetime', 'ASC')->first();
			$partner->user()->associate(User::find(Sentry::getUser()->id));
			$partner->salenextdatetime = DB::raw('DATE_ADD(NOW(), INTERVAL 30 MINUTE)');
			$partner->save();

			$partner->saveHistory("Клиент перешел к другому менеджеру: " . Sentry::getUser()->first_name . " " . Sentry::getUser()->last_name);

			$response = array(
					'status'	 => 'success',
					'partner'	 => $partner->toArray()
			);
		}

		return Response::json($response);
	}

}
