Забегая вперёд, сразу скажу, через API — никак. Но есть возможность его обойти.
С чего всё началось
Прижало мне, значит, в рамках одного корпоративного проекта сделать возможность в Bitrix24 массово добавлять задачи в план на день.

Кто не знает, план на день — это такой виджет (или как его правильнее назвать), отображающий список задач, которые ты планируешь сегодня выполнить. Добавить в него можно только существующие и только свои задачи (и, как потом оказалось, не только свои). Функционал особенно удобен, если задач много, а времени в сутках на них не хватает. Приоритизируешь задачи и собираешь свой рабочий день. Короче штука классная, но явно недоработанная.
В идеале, мне нужен был метод, в котором можно передать ID пользователя и список задач для добавления. Но в документации API Bitrix24 ничего такого не нашлось. ChatGPT тоже ничего не нашёл кроме метода task.planner.getlist, возвращающего список задач из текущего плана. ИИшка ожидаемо придумала методы а-ля task.planner.add и task.planner.delete, и на серьёзных щах стала предлагать решения, которые «точно работают».
После нескольких безуспешных попыток и обращения в техподдержку Bitrix24, выяснилось, что таких методов и нет вовсе. Смотреть план смотри, но редактировать нельзя.
Но раз через интерфейс CRM задачи добавляются, значит механизм такой предусмотрен, просто нужно глубже копнуть. Через devtools расковырял скрипты, которыми добавляется задача в план. Выяснилось, что там всё завязано на сессии пользователя и извне добавить кому-то в план задачу нельзя. Не совсем то, что мне хотелось, но хорошо хоть так.
POST-запрос в /bitrix/tools/intranet_planner.php создаёт задачу в плане юзера.
Нужно передать action, site_id и sessid.
Куки и сессию другого пользователя подставить в свой обработчик я не могу, а значит на стороннем ресурсе это выполнить нельзя, политика безопасности, все дела. Соответственно, выполнять действия нужно на домене CRMки. Но версия Bitrix24 у нас в компании облачная, поэтому редактировать её код возможности нет.
И единственный вариант, показавшийся мне подходящим — это сделать браузерное расширение, которое отлавливает в адресной строке определённый параметр и добавляет переданные в нём задачи в план.
Код выполняется на домене портала, ему доступны в BX‑методы, события и, главное, доступен sessid, а значит всё легально и почти удобно 🙂
Inject.js
(function () { const urlParams = new URLSearchParams(window.location.search); const raw = urlParams.get('set_to_plan'); if (!raw) return; const taskIds = raw .split(',') .map(id => parseInt(id.trim(), 10)) .filter(id => !isNaN(id)); if (taskIds.length === 0) { console.warn('[Bitrix Planner Inject] Неверный список задач'); return; } const run = async () => { const sessid = BX.bitrix_sessid(); const currentUserId = parseInt(BX.message('USER_ID'), 10); const taskInfoList = []; for (const id of taskIds) { try { const result = await BX.ajax.runAction('tasks.task.get', { data: { taskId: id } }); const task = result.data.task; if (parseInt(task.responsibleId, 10) === currentUserId) { taskInfoList.push({ id: task.id, title: task.title, responsible: task.responsibleId }); } else { console.log(`[Bitrix Planner Inject] Пропущена задача ${task.id} — ответственный другой пользователь`); } } catch (err) { console.warn(`[Bitrix Planner Inject] Не удалось получить задачу ${id}`, err); } } if (taskInfoList.length === 0) { console.log('[Bitrix Planner Inject] Нет задач для добавления (ни одна не принадлежит текущему пользователю)'); removeSetToPlanFromUrl(); return; } const postData = new URLSearchParams(); taskInfoList.forEach((task, i) => postData.append(`add[${i}]`, task.id)); fetch(`/bitrix/tools/intranet_planner.php?action=task&site_id=s1&sessid=${sessid}`, { method: 'POST', credentials: 'same-origin', headers: { 'Content-Type': 'application/x-www-form-urlencoded' }, body: postData.toString() }) .then(async resp => { const contentType = resp.headers.get("Content-Type") || ""; if (resp.ok && contentType.includes("application/json")) { console.log('[Bitrix Planner Inject] Добавлены задачи:', taskInfoList); showToast(taskInfoList); removeSetToPlanFromUrl(); } else { const text = await resp.text(); console.warn('[Bitrix Planner Inject] Не-JSON ответ:', text); } }) .catch(err => { console.error('[Bitrix Planner Inject] Ошибка запроса:', err); }); }; function showToast(taskList) { const content = taskList.map(t => `• ${t.title} (ID: ${t.id})`).join('<br>'); if (BX && BX.UI && BX.UI.Notification && BX.UI.Notification.Center) { BX.UI.Notification.Center.notify({ content: `Добавлены задачи в план:<br>${content}`, autoHideDelay: 5000, position: "top-right" }); } else { console.log('[Bitrix Planner Inject]', content); } } function removeSetToPlanFromUrl() { const url = new URL(window.location.href); url.searchParams.delete('set_to_plan'); window.history.replaceState({}, document.title, url.toString()); } if (typeof BX !== 'undefined' && typeof BX.ready === 'function') { BX.ready(run); } else { console.warn('[Bitrix Planner Inject] BX не определён'); } })();
Всё, что нужно, это перейти по ссылке вида: https://[ваш_портал].bitrix24.ru/company/personal/user/[ID_юзера]/tasks/?set_to_plan=[список_ID_задач]. Само собой нужно быть авторизованным в crm.
Обнаружив в строке параметр set_to_plan, скрипт обходит полученные задачи, сравнивает их исполнителя с ID пользователя в адресной строке. И если идентификаторы совпадают, добавляет задачу в план.
Если убрать проверку пользователя, то в план можно добавить любую существующую задачу. Никакого внутреннего механизма проверки в bitrix нет.
Рабочее расширение для Google Chrome и Яндекс браузера залил сюда, возможно кому-нибудь пригодится такая реализация. В других браузерах не проверял за ненадобностью.
Если интересно, зачем мне потребовалось массово добавлять задачи в план, то подписывайтесь на мой тг-канал и следите за обновлениями, расскажу там чуть позже 🙂
ссылка на оригинал статьи https://habr.com/ru/articles/904846/
Добавить комментарий