Files
rust-otus/smart-house/README.md
T
2026-04-27 23:02:53 +03:00

264 lines
17 KiB
Markdown

# Учебная библиотека "Умный дом"
Демонстрационная библиотека для выполнения домашних заданий.
## ДЗ 2025-12-16
Заготовка для библиотеки "Умный дом".
### Цель:
Создать заготовку для библиотеки «Умный дом» и напишите пример, демонстрирующий её функционал.
### Срок:
Сдать до: **2026-01-19**
### Описание/Пошаговая инструкция выполнения домашнего задания:
Библиотека и пример использования реализованы в одном package.
Для библиотеки:
- [x] Реализована в виде lib крейта.
- [x] Опишите тип: умный термометр. Тип должен предоставлять следующий функционал:
- [x] Конструктор, принимающий значения полей.
- [x] Возвращать значение текущей температуры (произвольное число).
- [x] Опишите тип: умная розетка. Тип должен предоставлять следующий функционал:
- [x] Конструктор, принимающий значения полей.
- [x] Включение/выключение + возможность узнать текущее состояние.
- [x] Возвращать текущую мощность: если выключено — ноль, иначе произвольное число.
- [x] Опишите тип: умное устройство. Тип должен содержать одно из устройств (умный термометр или розетку) и предоставлять следующий функционал:
- [x] Выводить в стандартный вывод сообщение о состоянии устройства.
- [x] Опишите тип: комната, содержащая массив умных устройств. Тип должен предоставлять следующий функционал:
- [x] Конструктор, принимающий массив устройств.
- [x] Можно получить ссылку на устройство по указанному индексу.
- [x] Можно получить мутабельную ссылку на устройство по указанному индексу.
- [x] Выводить в стандартный вывод отчёт о всех устройствах в комнате.
- [x] Опишите тип: умный дом, содержащий массив комнат. Тип должен предоставлять следующий функционал:
- [x] Конструктор, принимающий массив комнат.
- [x] Можно получить ссылку на комнату по указанному индексу.
- [x] Можно получить мутабельную ссылку на комнату по указанному индексу.
- [x] Выводить в стандартный вывод отчёт о всех комнатах.
- Размеры массивов можно выбрать произвольно.
- В случае, если указан индекс, выходящий за пределы массива, приложение должно аварийно завершаться (макрос `panic!()`).
Для примера использования:
- [x] Реализована в виде bin крейта.
- [x] Создайте экземпляр умного дома и выведете отчёт о его содержимом.
- [x] Для уже созданного экземпляра дома выключите умную розетку в одной из комнат. Снова выведите отчёт.
**Критерии оценки:**
- Package успешно собирается.
- Приложение-пример успешно выполняется и выводит отчёт о доме.
- Команды cargo clippy и cargo fmt --check не выводят ошибок и предупреждений.
- Присутствуют и успешно выполняются модульные тесты.
## ДЗ 2026-01-20
Дорабатываем умный дом
### Цель:
Дорабатываем функционал умного дома, используя возможности стандартной библиотеки.
### Срок:
Сдать до: **2026-02-11**
### Описание/Пошаговая инструкция выполнения домашнего задания:
Добавить обработку ошибок:
- [x] Заменить паники на возврат Option в методах получения комнаты по ключу.
- [x] Заменить паники на возврат Option в методах получения устройства по ключу.
Доработать хранение объектов:
- [x] Заменить массивы устройств и комнат на ассоциативные коллекции из std. В качестве ключей использовать строки.
- [x] Реализовать трейт Debug на всех типах.
- [x] Добавить возможность динамически добавлять/удалять устройства в комнату.
- [x] Добавить возможность динамически добавлять/удалять комнату в дом.
- [x] Добавить в тип умного дома метод, позволяющий сразу получить ссылку на умное устройство. Метод принимает имя комнаты
и имя устройства. В случае, если устройство или комната не найдены, возвращать тип ошибки, сообщающий, что именно
произошло. Тип ошибки должен реализовывать трейт `std::error::Error`.
- [x] Добавить реализации трейта `From`, позволяющие преобразовывать объекты умной розетки и умного термометра в объект
умного устройства.
- [x] Написать макрос для упрощенного создания комнаты, принимающий пары вида (ключ, объект умной розетки) или (ключ,
объект умного термометра) и возвращающий объект комнаты, содержащей все перечисленные устройства с
соответствующими ключами.
Доработать формирование отчёта:
- [x] Вынести метод формирования отчёта в трейт и реализовать его на всех типах, которые возвращают отчёт: умное устройство,
комната, дом.
Привести тесты в соответствие с новым функционалом.
Доработать приложение-пример:
- [x] Продемонстрировать возможность динамического добавления/удаления комнат.
- [x] Продемонстрировать возможность динамического добавления/удаления устройств.
- [x] Добавить функцию, которая принимает любой объект, умеющий выводить отчёт. Вывести с её помощью отчёты о доме,
отдельной комнате, отдельном устройстве.
- [x] Продемонстрировать возможность обработки ошибок.
**Критерии оценки:**
- Package успешно собирается.
- Приложение-пример успешно выполняется и выводит отчёт о доме.
- Команды cargo clippy и cargo fmt --check не выводят ошибок и предупреждений.
- Присутствуют и успешно выполняются модульные тесты.
## ДЗ 2026-02-12
Дорабатываем умные устройства
### Цель:
Описать для умной розетки и умного термометра логику взаимодействия с удалённым устройством и написать имитаторы устройств для тестирования.
### Срок:
Сдать до: **2026-03-04**
### Описание/Пошаговая инструкция выполнения домашнего задания:
Для типа умной розетки:
- [x] Функционал не изменяется: включение/выключение + запрос мощности.
- [x] Взаимодействие организовано синхронно, через TCP.
- [x] Розетка может использовать как реальный TCP-обмен, так и имитировать реальную работу (для тестов).
Для имитатора умной розетки:
- [x] Читает адрес для приёма TCP-соединений из аргументов командной строки.
- [x] Реализован с использованием неблокирующего сетевого взаимодействия.
- [x] Хранит состояние розетки.
- [x] Позволяет управлять розеткой множеству клиентов одновременно.
Для умного термометра:
- [x] Функционал не изменяется: возвращает температуру.
- [x] Получает значения температуры в виде UDP-пакетов в параллельном потоке.
- [x] Параллельный поток запускается при создании объекта термометра и завершается при уничтожении этого объекта.
- [x] Объект термометра возвращает последнее полученное значение температуры.
- [x] Термометр может имитировать удалённое получение данных о температуре (для тестов).
Для имитатора умного термометра:
- [x] Реализован с использованием неблокирующего сетевого взаимодействия.
- [x] Читает адрес для отправки UDP-пакетов и временной период отправки из файла.
- [x] Отправляет произвольное значение температуры на указанный адрес с указанной периодичностью.
Добавлен дополнительный пример умного дома с розетками и термометрами, которые работают с имитаторами. Данный пример должен запускаться и:
- [x] Выводить отчёт о состоянии дома, если имитаторы запущены.
- [x] Сообщать об ошибке, если устройству не удалось получить данные.
**Критерии оценки:**
- Package успешно собирается.
- Приложение-пример успешно выполняется.
- Команды cargo clippy и cargo fmt --check не выводят ошибок и предупреждений.
- Присутствуют и успешно выполняются модульные тесты.
### Запуск примеров
Запуск имитатора умной розетки:
cargo run --bin power_socket_mock -- 127.0.0.1:10001
Запуск имитатора термометра:
cargo run --bin thermometer_mock
Запуск примера умного дома:
cargo run --bin mocks_example
## ДЗ 2026-03-05
Паттерны в умном доме
### Цель:
Делаем код умного дома более удобным с использованием различных паттернов.
### Срок:
Сдать до: **2026-04-01**
### Описание/Пошаговая инструкция выполнения домашнего задания:
Реализовать билдер для умного дома, позволяющий инициализировать объект умного дома в [таком стиле](https://play.rust-lang.org/?version=stable&mode=debug&edition=2021&gist=5d0527e4684f726d54dc375829d983f4).
- [x] До добавления первой комнаты, билдер запрещает добавлять устройства. Это должно контролироваться компилятором.
Реализовать компоновщик для построения отчёта об объектах умного дома в [таком стиле](https://play.rust-lang.org/?version=stable&mode=debug&edition=2021&gist=c07dfc726e8ccbccdcc2d88a79d3f190).
- [x] Использовать статический полиморфизм (дженерики).
- [x] Вызов метода report() должен выводить в терминал отчёт обо всех добавленных объектах.
Добавить возможность добавления callback-ов в объект комнаты, которые срабатывают при добавлении новых устройств в комнату (паттерн Observer).
- [x] Использовать динамический полиморфизм (трейт-объекты).
- [x] Можно передавать как объект-subscriber, так и [замыкание](https://play.rust-lang.org/?version=stable&mode=debug&edition=2021&gist=06e9dc9bcce297d1e80a22d7e9338ee8).
Добавить example-ы, демонстрирующие новый функционал.
**Критерии оценки:**
- Package успешно собирается.
- Приложение-пример успешно выполняется.
- Команды cargo clippy и cargo fmt --check не выводят ошибок и предупреждений.
- Присутствуют и успешно выполняются модульные тесты.
### Демонстационные примеры
- `src/bin/house_builder.rs` - билдер для умного дома
- `src/bin/reporter.rs` - компоновщик для построения отчета
- `src/bin/subscribers.rs` - добавление коллбеков в объект комнаты
## ДЗ 2026-04-09
Си-style умная розетка
### Цель:
Реализуем Си ABI для работы с умной розеткой.
### Срок:
Сдать до: **2026-04-27**
### Описание/Пошаговая инструкция выполнения домашнего задания:
Реализовать workspace со следующими package-ами:
- [x] Библиотека умной розетки с Си ABI.
- [x] Приложение, использующее библиотеку умной розетки, линкуя её статически.
- [x] Приложение, использующее библиотеку умной розетки, линкуя её динамически в runtime.
Библиотека умной розетки с Си ABI:
- [x] Функционал не изменяется: включение/выключение + запрос мощности.
- [x] При сборке создаёт три артефакта:
1. Rust библиотеку
2. Статическую библиотеку с Си ABI.
3. Динамическую библиотеку с Си ABI
Пакеты-приложения должны демонстрировать функционал умной библиотеки.
**Критерии оценки:**
- Workspace успешно собирается.
- Приложения-примеры успешно выполняются.
- Команды cargo clippy, и cargo fmt --check не выводят ошибок и предупреждений.
### Демо
1. Собрать библиотеку:
cargo build -p power_socket_lib
2. Статическая линковка:
cargo run -p use_static
3. Динамическая линковка:
cargo run -p use_dynamic