• Модуль: imopenlines
  • Путь к файлу: ~/bitrix/modules/imopenlines/lib/session.php
  • Класс: BitrixImOpenLinesSession
  • Вызов: Session::finish
public function finish(bool $auto = false, bool $force = false, bool $hideChat = true): bool
{
	$result = false;

	Debug::addSession($this, __METHOD__, ['auto' => $auto, 'force' => $force, 'hideChat' => $hideChat]);
	if (!empty($this->session))
	{
		KpiManager::setSessionLastKpiMessageAnswered($this->session['ID']);

		$update = [];
		$messages = [];

		if ($force)
		{
			$this->session['CLOSED'] = 'Y';
			$update['FORCE_CLOSE'] = 'Y';
		}

		$currentDate = new DateTime();

		if ($this->session['CHAT_ID'])
		{
			$chatData = ChatTable::getById($this->session['CHAT_ID'])->fetch();
			$lastMessageId = $chatData['LAST_MESSAGE_ID'];
		}
		else
		{
			$lastMessageId = 0;
		}

		/*
		todo: Make new session config option to select that to set as date close - the last massage date either current date.
		if (
			$auto
			&& $lastMessageId > 0
		)
		{
			$messageData = MessageTable::getById($lastMessageId)->fetch();
			if ($messageData)
			{
				$currentDate = clone $messageData['DATE_CREATE'];
			}
		}
		*/

		$userViewChat = CIMContactList::InRecent($this->session['OPERATOR_ID'], IM_MESSAGE_OPEN_LINE, $this->session['CHAT_ID']);

		if (
			$this->session['CLOSED'] === 'Y'
			|| $this->session['SPAM'] === 'Y'
			|| ($this->session['WAIT_ACTION'] === 'Y' && $this->session['WAIT_ANSWER'] === 'N')
		)
		{
			$update['WAIT_ACTION'] = 'N';
			$update['WAIT_ANSWER'] = 'N';
			$update['CLOSED'] = 'Y';

			$messages[] = [
				'TO_CHAT_ID' => $this->session['CHAT_ID'],
				'FROM_USER_ID' => $this->session['OPERATOR_ID'],
				'MESSAGE' => Loc::getMessage('IMOL_SESSION_CLOSE_FINAL'),
				'SYSTEM' => 'Y',
				'RECENT_ADD'=> $userViewChat? 'Y': 'N',
				'PARAMS' => [
					'CLASS' => 'bx-messenger-content-item-ol-end',
					'TYPE' => 'lines',
					'COMPONENT_ID' => 'bx-imopenlines-message',
					'IMOL_VOTE_SID' => $this->session['ID'],
					'IMOL_VOTE_USER' => $this->session['VOTE'],
					'IMOL_VOTE_HEAD' => $this->session['VOTE_HEAD'],
					'IMOL_COMMENT_HEAD' => htmlspecialcharsbx($this->session['COMMENT_HEAD']),
				]
			];
		}
		else
		{
			if ($this->config['ACTIVE'] === 'N')
			{
				$update['WAIT_ACTION'] = 'N';
				$update['WAIT_ANSWER'] = 'N';
				$update['CLOSED'] = 'Y';

				$messages[] = [
					'TO_CHAT_ID' => $this->session['CHAT_ID'],
					'FROM_USER_ID' => $this->session['OPERATOR_ID'],
					'RECENT_ADD' => $userViewChat? 'Y': 'N',
					'MESSAGE'=> Loc::getMessage('IMOL_SESSION_CLOSE_FINAL'),
					'SYSTEM'=> 'Y',
					'PARAMS' => [
						'CLASS' => 'bx-messenger-content-item-ol-end',
						'TYPE' => 'lines',
						'COMPONENT_ID' => 'bx-imopenlines-message',
						'IMOL_VOTE_SID' => $this->session['ID'],
						'IMOL_VOTE_USER' => $this->session['VOTE'],
						'IMOL_VOTE_HEAD' => $this->session['VOTE_HEAD'],
						'IMOL_COMMENT_HEAD' => htmlspecialcharsbx($this->session['COMMENT_HEAD']),
					]
				];
			}
			else
			{
				$enableSystemMessage = $this->isEnableSendSystemMessage();
				$waitAction = false;

				if (
					$enableSystemMessage
					&& (
						(
							$auto
							&& $this->config['AUTO_CLOSE_RULE'] === self::RULE_TEXT
						)
						|| (
							!$auto
							&& $this->config['CLOSE_RULE'] === self::RULE_TEXT
						)
					)
				)
				{
					$messageCloseText = $this->config['CLOSE_TEXT'];

					if ($auto)
					{
						$this->chat->update([
							Chat::getFieldName(Chat::FIELD_SILENT_MODE) => 'N'
						]);

						$messageCloseText = $this->config['AUTO_CLOSE_TEXT'];
					}

					$messages[] = [
						'TO_CHAT_ID' => $this->session['CHAT_ID'],
						'FROM_USER_ID' => $this->session['OPERATOR_ID'],
						'MESSAGE' => $messageCloseText,
						'RECENT_ADD' => $userViewChat? 'Y': 'N',
						'SYSTEM' => 'Y',
						'IMPORTANT_CONNECTOR' => 'Y',
						'NO_SESSION_OL' => 'Y',
						'PARAMS' => [
							'CLASS' => 'bx-messenger-content-item-ol-output',
							'IMOL_FORM' => 'history',
							'TYPE' => 'lines',
							'COMPONENT_ID' => 'bx-imopenlines-message',
						]
					];

					$update['WAIT_ACTION'] = 'Y';
					$update['WAIT_ANSWER'] = 'N';
					$waitAction = true;
				}

				if (
					(
						$enableSystemMessage === true
						|| $this->isForcedSendVote === true
					)
					&& $this->config['VOTE_MESSAGE'] === 'Y'
					&& $this->session['CHAT_ID']
					&& empty($this->session['VOTE'])
				)
				{
					$paramsDateCloseVote = '';

					if (
						!empty((int)$this->config['VOTE_TIME_LIMIT'])
						&& (int)$this->config['VOTE_TIME_LIMIT'] > 0
					)
					{
						$dateCloseVote = new DateTime();
						$dateCloseVote->add(((int)$this->config['VOTE_TIME_LIMIT']) . ' SECONDS');
						//$dateCloseVote->add('15 SECONDS');
						$update['DATE_CLOSE_VOTE'] = $dateCloseVote;

						$paramsDateCloseVote = date('c', $dateCloseVote->getTimestamp());
					}

					$messages[] = [
						'TO_CHAT_ID' => $this->session['CHAT_ID'],
						'FROM_USER_ID' => $this->session['OPERATOR_ID'],
						'MESSAGE' => $this->config['VOTE_MESSAGE_2_TEXT'],
						'SYSTEM'=> 'Y',
						'RECENT_ADD' => $userViewChat? 'Y': 'N',
						'IMPORTANT_CONNECTOR' => 'Y',
						'NO_SESSION_OL' => 'Y',
						'PARAMS' => [
							'IMOL_VOTE' => $this->session['ID'],
							'IMOL_VOTE_TEXT' => $this->config['VOTE_MESSAGE_1_TEXT'],
							'IMOL_VOTE_LIKE' => $this->config['VOTE_MESSAGE_1_LIKE'],
							'IMOL_VOTE_DISLIKE' => $this->config['VOTE_MESSAGE_1_DISLIKE'],
							'IMOL_DATE_CLOSE_VOTE' => (string)$paramsDateCloseVote,
							'IMOL_TIME_LIMIT_VOTE' => (string)$this->config['VOTE_TIME_LIMIT'],
							'CLASS' => 'bx-messenger-content-item-ol-output bx-messenger-content-item-vote',
							'IMOL_FORM' => 'like',
							'TYPE' => 'lines',
							'COMPONENT_ID' => 'bx-imopenlines-message',
						]
					];

					$update['WAIT_ACTION'] = 'Y';
					$update['WAIT_ANSWER'] = 'N';
					$update['WAIT_VOTE'] = 'Y';
					$waitAction = true;
				}

				if ($waitAction !== true)
				{
					if ($auto)
					{
						$params = [
							'CLASS' => 'bx-messenger-content-item-ol-end'
						];
						if ($this->config['VOTE_MESSAGE'] === 'Y')
						{
							$params['TYPE'] = 'lines';
							$params['COMPONENT_ID'] = 'bx-imopenlines-message';
							$params['IMOL_VOTE_SID'] = $this->session['ID'];
							$params['IMOL_VOTE_USER'] = $this->session['VOTE'];
							$params['IMOL_VOTE_HEAD'] = $this->session['VOTE_HEAD'];
							$params['IMOL_COMMENT_HEAD'] = htmlspecialcharsbx($this->session['COMMENT_HEAD']);
						}
						$messages[] = [
							'TO_CHAT_ID' => $this->session['CHAT_ID'],
							'FROM_USER_ID' => $this->session['OPERATOR_ID'],
							'RECENT_ADD' => $userViewChat? 'Y': 'N',
							'MESSAGE' => Loc::getMessage('IMOL_SESSION_CLOSE_AUTO'),
							'SYSTEM' => 'Y',
							'PARAMS' => $params
						];
					}
					else
					{
						$userSkip = User::getInstance($this->chat->getData('OPERATOR_ID'));

						$params = [
							'CLASS' => 'bx-messenger-content-item-ol-end'
						];
						if ($this->config['VOTE_MESSAGE'] === 'Y')
						{
							$params['IMOL_VOTE_SID'] = $this->session['ID'];
							$params['IMOL_VOTE_USER'] = $this->session['VOTE'];
							$params['IMOL_VOTE_HEAD'] = $this->session['VOTE_HEAD'];
							$params['IMOL_COMMENT_HEAD'] = htmlspecialcharsbx($this->session['COMMENT_HEAD']);
						}
						$messages[] = [
							'TO_CHAT_ID' => $this->session['CHAT_ID'],
							'FROM_USER_ID' => $this->session['OPERATOR_ID'],
							'RECENT_ADD' => $userViewChat? 'Y': 'N',
							'MESSAGE' => Loc::getMessage(
								'IMOL_SESSION_CLOSE_' . $userSkip->getGender(),
								['#USER#' => '[USER=' . $userSkip->getId().'][/USER]']
							),
							'SYSTEM' => 'Y',
							'PARAMS' => $params
						];
					}

					$update['WAIT_ACTION'] = 'N';
					$update['WAIT_ANSWER'] = 'N';
					$update['CLOSED'] = 'Y';
				}

				if (!$auto)
				{
					if (!User::getInstance($this->session['OPERATOR_ID'])->isBot())
					{
						$update['DATE_OPERATOR_CLOSE'] = $currentDate;
					}
					if ($this->session['DATE_CREATE'] instanceof DateTime)
					{
						$update['TIME_CLOSE'] = $currentDate->getTimestamp() - $this->session['DATE_CREATE']->getTimestamp();
					}
				}
			}

			$update['DATE_MODIFY'] = $currentDate;
		}

		if (
			isset($update['CLOSED'])
			&& $update['CLOSED'] === 'Y'
		)
		{
			if ($this->session['CRM_ACTIVITY_ID'] > 0)
			{
				$crmManager = new Crm($this);
				if ($crmManager->isLoaded())
				{
					$crmManager->setSessionClosed(['DATE_CLOSE' => $currentDate]);
				}
			}

			$update['DATE_CLOSE'] = $currentDate;
			if (
				$this->session['TIME_CLOSE'] <= 0
				&& $this->session['DATE_CREATE'] instanceof DateTime
			)
			{
				$update['TIME_CLOSE'] = $update['DATE_CLOSE']->getTimestamp() - $this->session['DATE_CREATE']->getTimestamp();
			}
			if (
				$this->session['DATE_CREATE'] instanceof DateTime
				&& $this->session['TIME_BOT'] <= 0
				&& User::getInstance($this->session['OPERATOR_ID'])->isBot()
			)
			{
				$update['TIME_BOT'] = $update['DATE_CLOSE']->getTimestamp() - $this->session['DATE_CREATE']->getTimestamp();
			}
		}

		$this->update($update);

		// send messages
		foreach ($messages as $message)
		{
			$addMessageId = Im::addMessage($message);

			if (!empty($addMessageId))
			{
				$lastMessageId = $addMessageId;
			}
		}

		if (
			isset($update['CLOSED'])
			&& $update['CLOSED'] === 'Y'
			&& $this->session['CHAT_ID']
		)
		{
			$this->update([
				'END_ID' => $lastMessageId
			]);
		}

		if ($hideChat)
		{
			Im::chatHide($this->session['CHAT_ID']);
		}

		if (!empty($this->user['USER_CODE']))
		{
			$chatEntityId =	BitrixImOpenLinesChat::parseLinesChatEntityId($this->user['USER_CODE']);
			if (!empty($chatEntityId['connectorId']) && !empty($chatEntityId['connectorChatId']))
			{
				ImConnectorChat::deleteLastMessage($chatEntityId['connectorChatId'], $chatEntityId['connectorId']);
			}
		}

		if (
			isset($update['CLOSED'])
			&& $update['CLOSED'] === 'Y'
		)
		{
			$eventData = [];
			$eventData['RUNTIME_SESSION'] = $this;
			$eventData['SESSION'] = $this->session;
			$eventData['CONFIG'] = $this->config;
			$event = new MainEvent('imopenlines', 'OnSessionFinish', $eventData);
			$event->send();
		}

		$result = true;
	}

	return $result;
}