Заметки
После удаления лида у чата открытой линии может остаться CRM-привязка
Почему удаление лида из CRM не всегда очищает связь диалога открытой линии с CRM.
Если лид из открытой линии удалён, это ещё не значит, что чат полностью потерял связь с CRM. Перед повторным созданием лида нужно проверить старый CRM-контекст диалога.
Проблема
Лид, созданный из чата открытой линии, удалили из CRM. Потом по тому же чату нужно создать
новый лид, но повторный вызов imopenlines.crm.lead.create работает не так,
как ожидалось.
У диалога открытой линии может остаться техническая связь с CRM: сессия, чат, дело или привязки дела всё ещё хранят старый контекст. Из-за этого система может считать, что чат уже связан с CRM.
Обычно цепочка такая:
- по чату открытой линии был создан лид;
- у чата появилась CRM-привязка к лиду и делу;
- лид удалили из CRM;
- часть технических связей осталась;
- повторный вызов
imopenlines.crm.lead.createне создаёт новый лид ожидаемым образом; - перед повторным созданием нужно найти и очистить старую связь.
Проблема не в том, что удалённый лид продолжает существовать как обычная CRM-сущность. Чаще мешают оставшиеся связи между открытой линией, CRM-делом и чатом.
Что остаётся
Удаление лида не всегда очищает все связанные технические записи. Особенно если диалог открытой линии был связан не только с лидом, но и с CRM-делом.
У диалога открытой линии может быть отдельный CRM-контекст. Он нужен, чтобы связывать переписку с CRM и находить историю общения из карточки.
Проверять связь лучше не только по самому лиду. Следы могут остаться здесь:
- в сессии открытой линии;
- в данных чата;
- в CRM-деле, созданном для диалога;
- в привязках дела к CRM-сущностям;
- во внутренних таблицах связей.
Названия таблиц и набор полей лучше проверять на конкретной версии коробки. Внутренняя структура может отличаться.
Если у чата уже есть CRM-контекст, повторное создание лида через
imopenlines.crm.lead.create может не дать нового чистого лида.
Причина обычно в старых технических записях. Диалог всё ещё выглядит связанным с CRM, хотя сам лид уже удалён.
Поэтому перед повторным созданием нужно понять, где осталась связь: в чате, сессии, деле или привязках дела.
Решение
В коробочном Bitrix24 можно предварительно очистить CRM-контекст у сессии открытой линии и у чата. После этого лид создаётся уже без старой привязки.
Общая логика такая:
- найти сессию открытой линии;
- сбросить CRM-флаги у сессии;
- очистить ID CRM-дела у сессии;
- получить чат по
CHAT_ID; - очистить CRM-данные в полях чата;
- после этого отдельно запускать повторное создание лида.
Это работа с внутренними таблицами коробки. Перед применением нужен тестовый портал и резервная копия.
Пример кода
Пример очищает старую CRM-привязку у сессии открытой линии и у чата. Новый лид здесь не создаётся — это лучше делать отдельным шагом после проверки.
<?php
use Bitrix\Main\Loader;
use Bitrix\Im\Model\ChatTable;
use Bitrix\ImOpenLines\Model\SessionTable;
const IM_MODULE_ID = 'im';
const IMOPENLINES_MODULE_ID = 'imopenlines';
Loader::includeModule(IM_MODULE_ID);
Loader::includeModule(IMOPENLINES_MODULE_ID);
/**
* Очищает старую CRM-привязку у сессии и чата открытой линии.
*/
function clearOpenLineCrmBinding(array $session): void
{
$session_id = (int)($session['ID'] ?? 0);
$chat_id = (int)($session['CHAT_ID'] ?? 0);
if ($session_id <= 0 || $chat_id <= 0) {
return;
}
clearSessionCrmContext($session_id);
$chat = fetchChatById($chat_id);
if ($chat === null) {
return;
}
clearChatCrmContext($chat);
}
/**
* Сбрасывает CRM-контекст сессии открытой линии.
*/
function clearSessionCrmContext(int $session_id): void
{
SessionTable::update($session_id, [
'CRM' => 'N',
'CRM_CREATE' => 'N',
'CRM_CREATE_LEAD' => 'N',
'CRM_CREATE_COMPANY' => 'N',
'CRM_CREATE_CONTACT' => 'N',
'CRM_CREATE_DEAL' => 'N',
'CRM_ACTIVITY_ID' => '',
]);
}
/**
* Получает чат по ID.
*/
function fetchChatById(int $chat_id): ?array
{
$chat_result = ChatTable::getList([
'select' => [
'ID',
'ENTITY_DATA_1',
'ENTITY_DATA_2',
],
'filter' => [
'=ID' => $chat_id,
],
'limit' => 1,
]);
$chat = $chat_result->fetch();
return is_array($chat) ? $chat : null;
}
/**
* Очищает CRM-контекст в данных чата.
*/
function clearChatCrmContext(array $chat): void
{
$chat_id = (int)($chat['ID'] ?? 0);
if ($chat_id <= 0) {
return;
}
$entity_data_1 = resetChatEntityData((string)($chat['ENTITY_DATA_1'] ?? ''));
ChatTable::update($chat_id, [
'ENTITY_DATA_1' => $entity_data_1,
'ENTITY_DATA_2' => '',
]);
}
/**
* Очищает CRM-часть ENTITY_DATA_1.
*/
function resetChatEntityData(string $entity_data_1): string
{
if ($entity_data_1 === '') {
return '';
}
return '';
}
В примере ENTITY_DATA_1 очищается полностью. Если в конкретном портале
в этом поле хранятся ещё какие-то нужные данные, очистку нужно делать точечно.
Перед очисткой связи
Не стоит сразу чистить таблицы. Сначала нужно собрать картину: какой чат, какая сессия, какой лид и какое дело связаны между собой.
- проверить
CHAT_IDоткрытой линии; - найти последнюю сессию по этому чату;
- посмотреть CRM-поля сессии;
- проверить данные чата и его CRM-контекст;
- найти CRM-дело, связанное с диалогом;
- проверить привязки дела к удалённому лиду;
- сделать резервную копию перед очисткой.
Очистку лучше выполнять отдельным административным скриптом, а не в обработчике события и не в публичном ajax-действии.
Посмотреть CRM-контекст сессии
Этот пример ничего не очищает. Он находит последнюю сессию открытой линии по чату и выводит CRM-поля, которые полезно увидеть перед повторным созданием лида.
<?php
use Bitrix\Main\Loader;
use Bitrix\ImOpenLines\Model\SessionTable;
const IMOPENLINES_MODULE_ID = 'imopenlines';
const CHAT_ID = 0;
Loader::includeModule(IMOPENLINES_MODULE_ID);
$session_data = fetchLastOpenLineSession(CHAT_ID);
if ($session_data === null) {
echo 'Сессия открытой линии не найдена';
return;
}
printSessionCrmContext($session_data);
/**
* Получает последнюю сессию открытой линии по чату.
*/
function fetchLastOpenLineSession(int $chat_id): ?array
{
if ($chat_id <= 0) {
return null;
}
$session_result = SessionTable::getList([
'select' => [
'ID',
'CHAT_ID',
'CRM',
'CRM_ENTITY_TYPE',
'CRM_ENTITY_ID',
'CRM_ACTIVITY_ID',
],
'filter' => [
'=CHAT_ID' => $chat_id,
],
'order' => [
'ID' => 'DESC',
],
'limit' => 1,
]);
$session_data = $session_result->fetch();
return is_array($session_data) ? $session_data : null;
}
/**
* Выводит CRM-контекст сессии.
*/
function printSessionCrmContext(array $session_data): void
{
$context_data = [
'SESSION_ID' => $session_data['ID'] ?? null,
'CHAT_ID' => $session_data['CHAT_ID'] ?? null,
'CRM' => $session_data['CRM'] ?? null,
'CRM_ENTITY_TYPE' => $session_data['CRM_ENTITY_TYPE'] ?? null,
'CRM_ENTITY_ID' => $session_data['CRM_ENTITY_ID'] ?? null,
'CRM_ACTIVITY_ID' => $session_data['CRM_ACTIVITY_ID'] ?? null,
];
echo '<pre>';
print_r($context_data);
echo '</pre>';
} Если после удаления лида в сессии или чате всё ещё видны старые CRM-значения, значит перед повторным созданием лида нужно сначала разбирать эту привязку.