← Назад к справке

Модули коробки

Задачи

Рабочая справка по PHP API модуля tasks в коробочном Bitrix24: TaskTable, списки задач, участники, комментарии, логи, избранное и затраченное время.

Для чтения задач удобно использовать D7-таблицы. Для создания и изменения задач часто нужно отдельно проверять, какой API лучше подходит в конкретной версии коробки и должен ли код запускать права, уведомления и события.

Общее понимание

Модуль tasks содержит саму задачу и связанные таблицы: участников, чек-листы, теги, логи, избранное, таймеры и другие данные.

Подключение модуля

<?php

use Bitrix\Main\Loader;

Loader::includeModule('tasks');
<?php

use Bitrix\Main\Loader;

/**
 * Подключает модуль tasks.
 */
function requireTasksModule(): void
{
    if (!Loader::includeModule('tasks')) {
        throw new \RuntimeException('Не удалось подключить модуль tasks');
    }
}

requireTasksModule();

TaskTable и связанные таблицы

Класс Что хранит
\Bitrix\Tasks\TaskTable Основная сущность задачи.
\Bitrix\Tasks\Internals\Task\MemberTable Участники задачи.
\Bitrix\Tasks\Internals\Task\LogTable Логи изменений задачи.
\Bitrix\Tasks\Internals\Task\FavoriteTable Избранные задачи пользователя.
\Bitrix\Tasks\Internals\Task\ElapsedTimeTable Затраченное время.
\Bitrix\Tasks\Internals\Task\RelatedTable Зависимости задач.
\Bitrix\Tasks\Internals\Task\ReminderTable Напоминания по задачам.
\Bitrix\Tasks\Internals\Task\TagTable Теги задач.
\Bitrix\Tasks\Internals\Task\TimerTable Таймеры задач.

Карта методов

Метод или класс Что делает Когда использовать
TaskTable::getList() Получает задачи. Списки, отчёты, проверки по статусу и ответственному.
MemberTable::getList() Получает участников задачи. Когда нужны наблюдатели, соисполнители и роли.
LogTable::getList() Получает историю изменений задачи. Диагностика изменения статуса, срока, ответственного.
FavoriteTable::getList() Проверяет избранные задачи. Пользовательские списки и интерфейсные доработки.
ElapsedTimeTable::getList() Получает затраченное время. Отчёты по трудозатратам.
RelatedTable::getList() Получает связи и зависимости задач. Проверка предшествующих и связанных задач.
ReminderTable::getList() Получает напоминания. Диагностика уведомлений по задаче.
Comment::add() Добавляет комментарий к задаче. Автоматические комментарии из PHP.

ORM или старые классы

ORM хорошо подходит для чтения и отчётов. Если нужно создать или изменить задачу так, чтобы сработали права, уведомления и бизнес-логика, лучше отдельно проверить API конкретной версии коробки.

В старом коде часто встречаются CTasks, CTaskItem, CTaskCommentItem. В новых выборках чаще удобнее D7-таблицы.

Задачи

Базовое чтение задач через ORM.

Получить задачу

<?php

use Bitrix\Main\Loader;
use Bitrix\Tasks\TaskTable;

Loader::includeModule('tasks');

/**
 * Получает задачу по ID.
 */
function fetchTaskById(int $task_id): array
{
    if ($task_id <= 0) {
        return [];
    }

    $task = TaskTable::getList([
        'select' => [
            'ID',
            'TITLE',
            'STATUS',
            'RESPONSIBLE_ID',
            'CREATED_BY',
            'CREATED_DATE',
            'DEADLINE',
        ],
        'filter' => [
            '=ID' => $task_id,
        ],
        'limit' => 1,
    ])->fetch();

    return is_array($task) ? $task : [];
}

$task = fetchTaskById($task_id);

print_r($task);

Получить список задач

<?php

use Bitrix\Main\Loader;
use Bitrix\Tasks\TaskTable;

Loader::includeModule('tasks');

const TASK_LIMIT = 100;

/**
 * Получает задачи ответственного пользователя.
 */
function fetchUserTasks(int $responsible_id): array
{
    if ($responsible_id <= 0) {
        return [];
    }

    return TaskTable::getList([
        'select' => [
            'ID',
            'TITLE',
            'STATUS',
            'RESPONSIBLE_ID',
            'CREATED_BY',
            'DEADLINE',
        ],
        'filter' => [
            '=RESPONSIBLE_ID' => $responsible_id,
        ],
        'order' => [
            'ID' => 'DESC',
        ],
        'limit' => TASK_LIMIT,
    ])->fetchAll();
}

$tasks = fetchUserTasks($responsible_id);

print_r($tasks);

Задачи по статусу

<?php

use Bitrix\Main\Loader;
use Bitrix\Tasks\TaskTable;

Loader::includeModule('tasks');

const TASK_LIMIT = 100;

/**
 * Получает задачи пользователя по статусу.
 */
function fetchUserTasksByStatus(int $responsible_id, int $status): array
{
    if ($responsible_id <= 0) {
        return [];
    }

    return TaskTable::getList([
        'select' => [
            'ID',
            'TITLE',
            'STATUS',
            'RESPONSIBLE_ID',
            'CREATED_BY',
            'DEADLINE',
            'CREATED_DATE',
            'CHANGED_DATE',
            'CLOSED_DATE',
        ],
        'filter' => [
            '=RESPONSIBLE_ID' => $responsible_id,
            '=STATUS' => $status,
        ],
        'order' => [
            'DEADLINE' => 'ASC',
            'ID' => 'DESC',
        ],
        'limit' => TASK_LIMIT,
    ])->fetchAll();
}

$tasks = fetchUserTasksByStatus($responsible_id, $status);

print_r($tasks);

Участники задачи

Участники задачи хранятся отдельно. В зависимости от роли это могут быть ответственные, соисполнители, наблюдатели и другие участники.

<?php

use Bitrix\Main\Loader;
use Bitrix\Tasks\Internals\Task\MemberTable;

Loader::includeModule('tasks');

/**
 * Получает участников задачи.
 */
function fetchTaskMembers(int $task_id): array
{
    if ($task_id <= 0) {
        return [];
    }

    return MemberTable::getList([
        'select' => [
            'TASK_ID',
            'USER_ID',
            'TYPE',
        ],
        'filter' => [
            '=TASK_ID' => $task_id,
        ],
        'order' => [
            'USER_ID' => 'ASC',
        ],
    ])->fetchAll();
}

$members = fetchTaskMembers($task_id);

print_r($members);

Участники по ролям

<?php

use Bitrix\Main\Loader;
use Bitrix\Tasks\Internals\Task\MemberTable;

Loader::includeModule('tasks');

/**
 * Получает участников задачи по ролям.
 */
function fetchTaskMembersByType(int $task_id): array
{
    if ($task_id <= 0) {
        return [];
    }

    $members_by_type = [];

    $member_result = MemberTable::getList([
        'select' => [
            'TASK_ID',
            'USER_ID',
            'TYPE',
        ],
        'filter' => [
            '=TASK_ID' => $task_id,
        ],
        'order' => [
            'TYPE' => 'ASC',
            'USER_ID' => 'ASC',
        ],
    ]);

    while ($member = $member_result->fetch()) {
        $type = (string) $member['TYPE'];

        if (!isset($members_by_type[$type])) {
            $members_by_type[$type] = [];
        }

        $members_by_type[$type][] = (int) $member['USER_ID'];
    }

    return $members_by_type;
}

$members_by_type = fetchTaskMembersByType($task_id);

print_r($members_by_type);

Значения ролей лучше сверять на конкретной версии и реальных данных задачи.

Связанные данные

Комментарии, логи и избранное часто нужны для диагностики и отчётов по задачам.

Комментарии

Комментарии задач связаны с форумным модулем. Для добавления комментария есть интеграционный метод \Bitrix\Tasks\Integration\Forum\Task\Comment::add().

<?php

use Bitrix\Main\Loader;
use Bitrix\Tasks\Integration\Forum\Task\Comment;

Loader::includeModule('tasks');
Loader::includeModule('forum');

/**
 * Добавляет комментарий к задаче.
 */
function addTaskComment(int $task_id, int $author_id, string $message): array
{
    if ($task_id <= 0 || $author_id <= 0 || $message === '') {
        return [
            'is_success' => false,
            'comment_id' => 0,
            'error_messages' => ['Не заполнены данные комментария'],
        ];
    }

    $result = Comment::add($task_id, [
        'AUTHOR_ID' => $author_id,
        'POST_MESSAGE' => $message,
    ]);

    if (!$result->isSuccess()) {
        return [
            'is_success' => false,
            'comment_id' => 0,
            'error_messages' => $result->getErrorMessages(),
        ];
    }

    $data = $result->getData();

    return [
        'is_success' => true,
        'comment_id' => (int) ($data['ID'] ?? 0),
        'error_messages' => [],
    ];
}

$result = addTaskComment($task_id, $author_id, 'Комментарий из PHP');

print_r($result);

Изменить и удалить комментарий

В API комментариев задач также есть методы изменения и удаления. Перед использованием лучше проверить фактический набор обязательных параметров на версии коробки.

<?php

use Bitrix\Main\Loader;
use Bitrix\Tasks\Integration\Forum\Task\Comment;

Loader::includeModule('tasks');
Loader::includeModule('forum');

/**
 * Изменяет комментарий задачи.
 */
function updateTaskComment(int $task_id, int $comment_id, int $author_id, string $message): array
{
    if ($task_id <= 0 || $comment_id <= 0 || $author_id <= 0 || $message === '') {
        return [
            'is_success' => false,
            'error_messages' => ['Не заполнены данные комментария'],
        ];
    }

    $result = Comment::update($task_id, $comment_id, [
        'AUTHOR_ID' => $author_id,
        'POST_MESSAGE' => $message,
    ]);

    return [
        'is_success' => $result->isSuccess(),
        'error_messages' => $result->getErrorMessages(),
    ];
}

/**
 * Удаляет комментарий задачи.
 */
function deleteTaskComment(int $task_id, int $comment_id, int $author_id): array
{
    if ($task_id <= 0 || $comment_id <= 0 || $author_id <= 0) {
        return [
            'is_success' => false,
            'error_messages' => ['Не заполнены данные комментария'],
        ];
    }

    $result = Comment::delete($task_id, $comment_id, [
        'AUTHOR_ID' => $author_id,
    ]);

    return [
        'is_success' => $result->isSuccess(),
        'error_messages' => $result->getErrorMessages(),
    ];
}

Логи задачи

<?php

use Bitrix\Main\Loader;
use Bitrix\Tasks\Internals\Task\LogTable;

Loader::includeModule('tasks');

/**
 * Получает последние изменения задачи.
 */
function fetchTaskLogItems(int $task_id): array
{
    if ($task_id <= 0) {
        return [];
    }

    return LogTable::getList([
        'select' => [
            'ID',
            'TASK_ID',
            'USER_ID',
            'FIELD',
            'FROM_VALUE',
            'TO_VALUE',
            'CREATED_DATE',
        ],
        'filter' => [
            '=TASK_ID' => $task_id,
        ],
        'order' => [
            'ID' => 'DESC',
        ],
        'limit' => 100,
    ])->fetchAll();
}

$log_items = fetchTaskLogItems($task_id);

print_r($log_items);

Избранное

<?php

use Bitrix\Main\Loader;
use Bitrix\Tasks\Internals\Task\FavoriteTable;

Loader::includeModule('tasks');

/**
 * Проверяет, добавлена ли задача в избранное у пользователя.
 */
function hasFavoriteTask(int $task_id, int $user_id): bool
{
    if ($task_id <= 0 || $user_id <= 0) {
        return false;
    }

    $favorite = FavoriteTable::getList([
        'select' => [
            'TASK_ID',
            'USER_ID',
        ],
        'filter' => [
            '=TASK_ID' => $task_id,
            '=USER_ID' => $user_id,
        ],
        'limit' => 1,
    ])->fetch();

    return is_array($favorite);
}

$has_favorite = hasFavoriteTask($task_id, $user_id);

var_dump($has_favorite);

Затраченное время

<?php

use Bitrix\Main\Loader;
use Bitrix\Tasks\Internals\Task\ElapsedTimeTable;

Loader::includeModule('tasks');

/**
 * Получает записи затраченного времени по задаче.
 */
function fetchTaskElapsedTimeItems(int $task_id): array
{
    if ($task_id <= 0) {
        return [];
    }

    return ElapsedTimeTable::getList([
        'select' => [
            'ID',
            'TASK_ID',
            'USER_ID',
            'MINUTES',
            'COMMENT_TEXT',
            'CREATED_DATE',
        ],
        'filter' => [
            '=TASK_ID' => $task_id,
        ],
        'order' => [
            'ID' => 'DESC',
        ],
    ])->fetchAll();
}

$elapsed_time_items = fetchTaskElapsedTimeItems($task_id);

print_r($elapsed_time_items);

Напоминания

<?php

use Bitrix\Main\Loader;
use Bitrix\Tasks\Internals\Task\ReminderTable;

Loader::includeModule('tasks');

/**
 * Получает напоминания задачи.
 */
function fetchTaskReminders(int $task_id): array
{
    if ($task_id <= 0) {
        return [];
    }

    return ReminderTable::getList([
        'select' => [
            '*',
        ],
        'filter' => [
            '=TASK_ID' => $task_id,
        ],
        'order' => [
            'ID' => 'ASC',
        ],
    ])->fetchAll();
}

$reminders = fetchTaskReminders($task_id);

print_r($reminders);

Состав полей напоминаний лучше вывести через getMap() или print_r() результата на своём портале.

Источники