id_task) { $this->addError('id_task', 'Задача не указана'); } if (!$this->id_accounts) { $this->addError('id_accounts', 'Пользователь не указан'); } if (!$this->text || trim($this->text) === '') { $this->addError('text', 'Текст комментария не может быть пустым'); } if ($errors = $this->getErrors()) { return $errors; } // Проверяем что задача существует Task::check_task($this->id_task); // Если это ответ — проверяем что родительский комментарий существует if ($this->id_answer) { self::checkComment($this->id_answer); } // Вставляем в базу Database::insert($this->db_name, [ 'id_task' => $this->id_task, 'id_accounts' => $this->id_accounts, 'id_answer' => $this->id_answer ?: null, 'text' => $this->text, 'date_create' => date('Y-m-d H:i:s'), 'file_img' => '[]' ]); $this->id = Database::id(); // Возвращаем созданный комментарий с данными пользователя return [ 'success' => true, 'comment' => $this->getById($this->id) ]; } // Обновление комментария public function update() { static::$error_message = []; // Валидация if (!$this->id) { $this->addError('id', 'ID комментария не указан'); } if (!$this->text || trim($this->text) === '') { $this->addError('text', 'Текст комментария не может быть пустым'); } if ($errors = $this->getErrors()) { return $errors; } // Проверяем что комментарий существует $comment = self::checkComment($this->id); // Проверяем что пользователь — автор комментария if ((int)$comment['id_accounts'] !== (int)$this->id_accounts) { $this->addError('access', 'Вы можете редактировать только свои комментарии'); return $this->getErrors(); } // Обновляем в БД Database::update($this->db_name, [ 'text' => $this->text ], [ 'id' => $this->id ]); return [ 'success' => true, 'comment' => $this->getById($this->id) ]; } // Удаление комментария (с дочерними) public static function delete($id, $id_accounts) { // Проверяем что комментарий существует $comment = self::checkComment($id); // Получаем задачу для проверки админа проекта $task = Database::get('cards_task', ['id_project'], ['id' => $comment['id_task']]); // Проверяем права: автор комментария ИЛИ админ проекта $isAuthor = (int)$comment['id_accounts'] === (int)$id_accounts; $isProjectAdmin = $task && ProjectAccess::isAdmin($task['id_project'], $id_accounts); if (!$isAuthor && !$isProjectAdmin) { RestApi::response([ 'success' => false, 'errors' => ['access' => 'Нет прав на удаление комментария'] ], 403); } // Рекурсивно удаляем все дочерние комментарии self::deleteWithChildren($id); return ['success' => true]; } // Рекурсивное удаление комментария и всех его дочерних private static function deleteWithChildren($id) { // Находим все дочерние комментарии $children = Database::select('comments', ['id'], ['id_answer' => $id]); // Рекурсивно удаляем дочерние if ($children) { foreach ($children as $child) { self::deleteWithChildren($child['id']); } } // Удаляем папку с файлами комментария FileUpload::deleteFolder('comment', $id); // Удаляем сам комментарий Database::delete('comments', ['id' => $id]); } // Удаление комментария (проверка прав уже выполнена на уровне API) public static function deleteWithAccess($id) { // Рекурсивно удаляем все дочерние комментарии self::deleteWithChildren($id); return ['success' => true]; } // === МЕТОДЫ ДЛЯ РАБОТЫ С ФАЙЛАМИ === // Загрузка файла к комментарию (проверка прав уже выполнена на уровне API) public static function uploadFileSimple($comment_id, $file_base64, $file_name) { return FileUpload::upload('comment', $comment_id, $file_base64, $file_name); } // Удаление файлов комментария (проверка прав уже выполнена на уровне API) public static function deleteFileSimple($comment_id, $file_names) { return FileUpload::delete('comment', $comment_id, $file_names); } // Загрузка файла к комментарию (только автор может загружать) - DEPRECATED public static function uploadFile($comment_id, $file_base64, $file_name, $user_id) { // Проверка что комментарий существует $comment = self::checkComment($comment_id); // Проверка что пользователь — автор комментария if ((int)$comment['id_accounts'] !== (int)$user_id) { RestApi::response([ 'success' => false, 'errors' => ['access' => 'Вы можете загружать файлы только к своим комментариям'] ], 403); } return FileUpload::upload('comment', $comment_id, $file_base64, $file_name); } // Удаление файлов комментария (автор или админ проекта) - DEPRECATED public static function deleteFile($comment_id, $file_names, $user_id) { // Проверка что комментарий существует $comment = self::checkComment($comment_id); // Получаем задачу для проверки админа проекта $task = Database::get('cards_task', ['id_project'], ['id' => $comment['id_task']]); // Проверка прав: автор комментария ИЛИ админ проекта $isAuthor = (int)$comment['id_accounts'] === (int)$user_id; $isProjectAdmin = $task && ProjectAccess::isAdmin($task['id_project'], $user_id); if (!$isAuthor && !$isProjectAdmin) { RestApi::response([ 'success' => false, 'errors' => ['access' => 'Нет прав на удаление файлов'] ], 403); } return FileUpload::delete('comment', $comment_id, $file_names); } // Получение комментария по ID (с данными пользователя) public function getById($id) { $comment = Database::get($this->db_name, [ '[>]accounts' => ['id_accounts' => 'id'] ], [ 'comments.id', 'comments.id_task', 'comments.id_accounts', 'comments.id_answer', 'comments.text', 'comments.date_create', 'comments.file_img', 'accounts.name(author_name)', 'accounts.avatar_url(author_avatar)' ], [ 'comments.id' => $id ]); // Декодируем JSON файлов if ($comment) { $comment['file_img'] = $comment['file_img'] ? json_decode($comment['file_img'], true) : []; } return $comment; } // Получение всех комментариев задачи public function getByTask($id_task) { // Проверяем что задача существует Task::check_task($id_task); $comments = Database::select($this->db_name, [ '[>]accounts' => ['id_accounts' => 'id'] ], [ 'comments.id', 'comments.id_task', 'comments.id_accounts', 'comments.id_answer', 'comments.text', 'comments.date_create', 'comments.file_img', 'accounts.name(author_name)', 'accounts.avatar_url(author_avatar)' ], [ 'comments.id_task' => $id_task, 'ORDER' => ['comments.date_create' => 'ASC'] ]); // Декодируем JSON файлов для каждого комментария return array_map(function($comment) { $comment['file_img'] = $comment['file_img'] ? json_decode($comment['file_img'], true) : []; return $comment; }, $comments ?: []); } // Проверка и получение комментария (при ошибке — сразу ответ и exit) public static function checkComment($id) { $comment = Database::get('comments', '*', ['id' => $id]); if (!$id || !$comment) { RestApi::response(['success' => false, 'errors' => ['comment' => 'Комментарий не найден']], 404); } return $comment; } } ?>