📝 Задания мини-проекта Agile Projects
⚡ Все задачи — кратко
- Задание 1: Модуль apps/, приложение tasks, модель Tag (name, MinLengthValidator(4)), миграции, коммит
- Задание 2: Приложение projects, модель Project (name unique, description, created_at, Meta ordering), миграции, коммит
- Задание 3: Модель ProjectFile (file_name, file_path, created_at), связь M2M Project ↔ ProjectFile, @property count_of_files, миграции
- Задание 4: Модель Task (все поля: FK к Project и User, M2M к Tag, Enum Statuses/Priority, deadline=конец_месяца, unique_together), миграции
- Задание 5: TagSerializer, TagListAPIView (GET список + POST создание), URL /api/v1/tags/
- Задание 6: TagDetailAPIView (GET/PUT/DELETE по pk), URL /api/v1/tags/<pk>/
- Задание 7: AllProjectsSerializer + CreateProjectSerializer (валидация description ≥ 30 символов), ProjectsListAPIView (GET с фильтром дат + POST), URL /api/v1/projects/
- Задание 8: ProjectDetailSerializer, ProjectDetailAPIView (GET/PUT с partial=True/DELETE), URL /api/v1/projects/<pk>/
- Задание 9: upload_file_helpers (check_extension, check_file_size, create_file_path, save_file), сериализаторы файлов, ProjectFileListAPIView (GET + POST), URL /api/v1/projects/files/
Контекст: Вы — Python-разработчик в крупной компании и получили новый проект от клиента — «Agile Projects». Этот проект — будущая веб-платформа для управления проектами, задачами и сотрудниками, ориентированной на использование в рамках Agile-методологии. Платформа реализуется на Django + DRF с REST API.
Задание 1 — Создание приложений, регистрация первой модели Tag
- Для большего контроля и чистоты архитектуры создайте модуль
apps, переместите только что созданное приложение в этот модуль. - Создайте первое приложение
tasks. - Зарегистрируйте новое приложение в настройках Django.
- Создайте модуль
modelsв приложенииtasksи создайте первую модельTagв файлеtag.py:name(строковое поле, максимальная длина 20, минимальная длина — 4)- Строковое отображение объекта должно быть в виде его имени (магический метод
__str__)
- Проведите миграции, убедитесь, что всё работает, запустив сервер.
- Зафиксируйте все изменения, сделайте запрос на слияние.
Задание 2 — Второе приложение и модель Project
- Создайте приложение
projects. - Зарегистрируйте новое приложение в настройках Django.
- Создайте модуль
modelsв приложенииprojectsи создайте первую модельProjectв файлеproject.py:name(строковое поле, максимальная длина 100, уникальное)description(большое строковое поле, обязательно к заполнению)created_at— поле даты и времени, заполняется автоматически при создании проекта- Строковое отображение объекта должно быть в виде его имени (
__str__) - Определение класса
Metaдля сортировки проектов по их имени
- Проведите миграции, убедитесь, что всё работает, запустив сервер.
- Зафиксируйте все изменения, сделайте запрос на слияние.
Задание 3 — Модель файлов, построение связи с проектами
- В приложении
projectsсоздайте новую модельProjectFile:file_name— строковое поле, максимальная длина 120 символовfile_path— поле загрузки файлов, таргет сохранения — папкаdocumentscreated_at— дата создания файла, автозаполняется при создании нового файла- Отображение объектов по полю
file_name(магический метод__str__) - Сортировка записей по дате создания в порядке убывания
- В модели
Projectсоздайте новое полеfiles, которое будет связывать проекты и файлы связью «Многие ко Многим», связующее поле —project. - В модели
Projectдобавьте динамическое полеcount_of_filesчерез декоратор@property, которое будет высчитывать количество файлов для проекта. - Проведите миграции, убедитесь, что всё работает, запустив сервер.
- Зафиксируйте все изменения, сделайте запрос на слияние.
Задание 4 — Модель Задач, связь с проектами и пользователями
- В приложении
tasksсоздайте новую модельTask:name— строковое поле, максимальное значение 120 символовdescription— большое строковое поле, обязательно к заполнениюstatus— строковое поле, max 15 символов, выбор из Enum классаStatuses, значение по умолчанию —NEWpriority— цифровое маленькое поле, выбор из Enum классаPriority, значение по умолчанию —MEDIUMproject— ForeignKey к моделиProject, при удалении проекта все задачи удаляются, related_name —taskstags— ManyToMany к моделиTag, related_name —taskscreated_at— дата и время, автозаполнение при созданииupdated_at— дата и время, автозаполнение при создании и обновленииdeleted_at— дата и время, может быть пустымdeadline— дата и время, обязательно. По умолчанию — расчёт последнего дня текущего месяца при созданииassignee— ForeignKey к моделиUserот Django, защита от удаления, related_name —tasks, может отсутствовать
- Добавьте строковое отображение задач в формате: «название задачи, статус».
- Добавьте сортировку по дедлайн-дате в порядке убывания.
- Добавьте уникальность по полям
nameиproject. - Проведите миграции, убедитесь, что всё работает, запустив сервер.
- Зафиксируйте все изменения, сделайте запрос на слияние.
Задание 5 — Получение списка всех тегов и создание нового тега
- В приложении
tasksудалите файлviews.py, создайте модульviews. - В модуле
viewsсоздайте новый файлtag_views.py. - В приложении
tasksсоздайте новый модульserializers. - В модуле
serializersсоздайте новый файлtag_serializers.py. - Напишите сериализатор для работы с тегами (так как у нас всего одно поле в этой модели, сериализатор будет один на все будущие запросы).
- Напишите классовое отображение:
- Реализовать метод для получения всех объектов
Tag - Для получения списка всех тегов методом
get - Для создания нового тега методом
post
- Реализовать метод для получения всех объектов
- Зарегистрируйте новое классовое отображение в списке эндпоинтов.
- Проверьте работу нашего классового отображения.
- Зафиксируйте все изменения, сделайте запрос на слияние.
Задание 6 — Получение, обновление и удаление тега
- В файле
tag_views.pyсоздайте новый классTagDetailAPIView. - Напишите отдельный метод, который позволит получать конкретный объект по его id.
- Реализуйте метод
getдля получения конкретного тега. - Реализуйте метод
putдля возможности обновления информации о теге (обновление поля name). - Реализуйте метод
deleteдля возможности удалить конкретный тег по его id. - Проверьте работу нашего классового отображения.
- Зафиксируйте все изменения, сделайте запрос на слияние.
Задание 7 — Получение списка проектов и создание нового проекта
- В приложении
projectsсоздайте модулиserializers,views, удалите файлviews.py. - В модуле
serializersсоздайте файлproject_serializers.py. - Создайте первый сериализатор
AllProjectsSerializerна получение информации о всех проектах. Отображаемые поля:id,name,created_at. - В модуле
viewsсоздайте файлproject_views.py, напишите классовое отображение:- Реализуйте метод на получение списка всех проектов:
- Получить из
query_paramsзначения датdate_from,date_to - Если никаких значений передано не было — получить список полностью всех проектов
- Если были переданы значения для временного диапазона — сконвертировать полученные значения по текущей временной зоне (поможет метод
make_aware()и модульtimezoneв Django) - Провести фильтрацию по диапазону дат
date_from—date_to
- Получить из
- Реализуйте метод
getна отображение списка всех проектов, добавьте фильтрацию черезquery_paramsна получение проектов в определённом временном промежутке - Реализуйте метод на создание нового проекта
- Реализуйте метод на получение списка всех проектов:
- Зарегистрируйте новое отображение в файле
urls.pyв приложенииprojects. - Проверьте работу нашего классового отображения.
- Зафиксируйте все изменения, сделайте запрос на слияние.
Задание 8 — Получение, обновление и удаление проекта
- Создайте новый сериализатор
ProjectDetailSerializerдля получения конкретной информации по проекту:- name
- description
- created_at
- count_of_files
- Напишите новый класс-отображение
ProjectDetailAPIViewдля получения конкретного проекта, обновления и удаления проекта.- При обновлении полученного проекта добавьте возможность частичного обновления полей.
- Зарегистрируйте новый эндпоинт, проверьте как отрабатывают запросы GET, PUT, DELETE.
- Зафиксируйте все изменения, сделайте запрос на слияние.
Задание 9 — Работа с файлами
- В приложении
projectsсоздайте новый модульutils. - Создайте в этом модуле файл
upload_file_helpers.py. - В этом файле необходимо создать функции:
- Функция на проверку валидных расширений файла
- Функция на проверку размерности файла (файл не должен быть больше 2 MB)
- Функция на создание пути для сохранения файла
- Функция на сохранение файла (файл должен записываться по частям для избежания потенциальных ошибок и потери данных)
- В модуле
serializersв приложенииprojectsсоздайте новый файлproject_file_serializers.py. - Создайте сериализатор
AllProjectFilesSerializerдля отображения краткой информации по всем файлам:id,file_name,project. - Создайте сериализатор
CreateProjectFileSerializerдля создания нового файла:- Для создания необходимо только поле
file_name - Поле
file_nameнеобходимо валидировать:- Проверка на наличие символов из таблицы ASCII
- Проверка на доступные расширения файлов (pdf, csv, doc, xlsx)
- Для создания необходимо только поле
- Переопределите метод
create:- Перед сохранением файла необходимо создать путь для сохранения
- Также необходимо получить из тела запроса сам файл и проверить его на размерность (не более 2 MB)
- Если файл проходит все проверки — сохранить его в проекте, сохранить объект файла
- Если файл слишком большой — поднять исключение валидации с сообщением об ошибке
- Напишите класс-отображение
ProjectFileListAPIViewдля получения списка всех файлов:- Реализовать метод на получение всех файлов для конкретного проекта по имени проекта. Если имя проекта не было передано — выводить список полностью всех файлов.
- Добавьте в класс-отображение
ProjectFileListAPIViewметодpostдля создания нового файла и привязки его к конкретному проекту (проект получать через полеid, которое будет передаваться в теле запроса). - Зарегистрируйте новый эндпоинт, проверьте как отрабатывают запросы GET, POST.
- Зафиксируйте все изменения, сделайте запрос на слияние.