Files
challenge-pl/UPDATE.md

8.1 KiB
Raw Blame History

Добавление поля learningMaterial в задачу челленджа

Описание изменений

В модель задачи челленджа (ChallengeTask) добавлено новое необязательное текстовое поле learningMaterial для хранения дополнительной обучающей информации в формате Markdown.

Структура данных

Модель ChallengeTask

{
  title: string,           // Заголовок задания (обязательное)
  description: string,     // Основное описание в Markdown (обязательное, видно студентам)
  learningMaterial: string, // Дополнительный учебный материал в Markdown (необязательное, видно студентам)
  hiddenInstructions: string, // Скрытые инструкции для LLM (необязательное, только для преподавателей)
  createdAt: Date,         // Дата создания
  updatedAt: Date,         // Дата последнего обновления
  creator: Object          // Данные создателя из Keycloak
}

Изменения в API

1. Создание задания (POST /challenge/task)

Добавлено поле в тело запроса:

{
  "title": "Название задания",
  "description": "Основное описание в Markdown",
  "learningMaterial": "Дополнительный учебный материал в Markdown",
  "hiddenInstructions": "Скрытые инструкции для преподавателей"
}

Пример запроса:

POST /challenge/task
Content-Type: application/json

{
  "title": "Реализация алгоритма сортировки",
  "description": "Напишите функцию сортировки массива методом пузырька",
  "learningMaterial": "## Теория\n\nМетод пузырьковой сортировки работает путем...\n\n## Полезные ссылки\n- [Википедия](https://ru.wikipedia.org/wiki/Сортировка_пузырьком)\n- [Видео объяснение](https://example.com/video)",
  "hiddenInstructions": "Оценить эффективность алгоритма и стиль кода"
}

2. Обновление задания (PUT /challenge/task/:taskId)

Добавлено поле в тело запроса:

{
  "title": "Новое название",
  "description": "Обновленное описание",
  "learningMaterial": "Обновленный учебный материал",
  "hiddenInstructions": "Обновленные инструкции"
}

Получение данных

Получение задания (GET /challenge/task/:taskId)

Ответ содержит новое поле:

{
  "id": "task_id",
  "title": "Название задания",
  "description": "Основное описание в Markdown",
  "learningMaterial": "Дополнительный учебный материал в Markdown",
  "createdAt": "2025-01-15T10:00:00.000Z",
  "updatedAt": "2025-01-15T10:30:00.000Z"
}

Важно: Поле learningMaterial видно всем пользователям (студентам и преподавателям), в отличие от hiddenInstructions, которое скрывается от студентов.

Получение всех заданий (GET /challenge/tasks)

Возвращает массив заданий с новым полем learningMaterial.

Получение цепочек (GET /challenge/chains, GET /challenge/chain/:chainId)

При получении цепочек с populate заданий, поле learningMaterial будет доступно в каждом задании цепочки.

Frontend изменения

Интерфейсы TypeScript

interface ChallengeTask {
  id: string;
  title: string;
  description: string;     // Markdown
  learningMaterial?: string; // Новое поле - дополнительный материал в Markdown
  createdAt: string;
  updatedAt: string;
}

Формы создания/редактирования заданий

В формах создания и редактирования заданий необходимо добавить поле для ввода learningMaterial:

// Пример компонента формы
const TaskForm = () => {
  const [formData, setFormData] = useState({
    title: '',
    description: '',
    learningMaterial: '', // Новое поле
    hiddenInstructions: ''
  });

  // Визуальный редактор или textarea для learningMaterial
  return (
    <form>
      <input name="title" value={formData.title} />
      <textarea name="description" value={formData.description} />

      {/* Новое поле для дополнительного материала */}
      <label>Дополнительный учебный материал (Markdown)</label>
      <textarea
        name="learningMaterial"
        value={formData.learningMaterial}
        placeholder="Дополнительные объяснения, ссылки, примеры..."
      />

      {/* Только для преподавателей */}
      <textarea name="hiddenInstructions" value={formData.hiddenInstructions} />
    </form>
  );
};

Отображение заданий

При отображении задания студентам показывать learningMaterial как дополнительную информацию:

const TaskView = ({ task }: { task: ChallengeTask }) => {
  return (
    <div>
      <h1>{task.title}</h1>

      {/* Основное описание */}
      <div dangerouslySetInnerHTML={{ __html: marked(task.description) }} />

      {/* Дополнительный учебный материал */}
      {task.learningMaterial && (
        <div className="learning-material">
          <h2>Дополнительные материалы</h2>
          <div dangerouslySetInnerHTML={{ __html: marked(task.learningMaterial) }} />
        </div>
      )}
    </div>
  );
};

Миграция данных

Поле learningMaterial добавлено как необязательное с значением по умолчанию '', поэтому:

  • Существующие задания будут работать без изменений
  • Новое поле будет пустым для старых заданий
  • Можно постепенно добавлять учебный материал к существующим заданиям

Тестирование

Создание задания с учебным материалом

# Создать задание с дополнительным материалом
POST /challenge/task
{
  "title": "Тестовое задание",
  "description": "Основное задание",
  "learningMaterial": "# Полезная информация\n\nЭто дополнительный материал для студентов"
}

Получение задания

GET /challenge/task/{taskId}
# Проверить, что learningMaterial присутствует в ответе

Обновление учебного материала

PUT /challenge/task/{taskId}
{
  "learningMaterial": "# Обновленная информация\n\nНовые полезные материалы..."
}

Влияние на существующий код

  • Все существующие эндпоинты получения данных автоматически возвращают новое поле
  • Создание заданий без указания learningMaterial работает как прежде
  • Фильтрация и валидация не затрагиваются
  • Поле индексируется MongoDB автоматически