diff --git a/.coverage b/.coverage new file mode 100644 index 000000000..38fbb0475 Binary files /dev/null and b/.coverage differ diff --git a/README.md b/README.md index 272081708..aa88c1975 100644 --- a/README.md +++ b/README.md @@ -11,14 +11,24 @@ ### Структура проекта - `praktikum` - пакет, содержащий код программы -- `tests` - пакет, содержащий тесты, разделенные по классам. Например, `bun_test.py`, `burger_test.py` и т.д. +- `tests` - пакет, содержащий тесты, разделенные по классам: +- Для `Bun` и `Ingredient` использована параметризация +- Для `Burger` использованы моки +- Для `Database` проверяются типы и контрольные значения ### Запуск автотестов **Установка зависимостей** -> `$ pip install -r requirements.txt` +> `pip install -r requirements.txt` **Запуск автотестов и создание HTML-отчета о покрытии** - -> `$ pytest --cov=praktikum --cov-report=html` +python -m pytest -v +python -m pytest --cov=praktikum --cov-report=html + +## Покрытие +```bash +python -m pytest -v +python -m pytest --cov=praktikum --cov-report=term-missing +python -m pytest --cov=praktikum --cov-report=html +``` \ No newline at end of file diff --git a/ingredient_types.py b/ingredient_types.py deleted file mode 100644 index 34940ad5d..000000000 --- a/ingredient_types.py +++ /dev/null @@ -1,7 +0,0 @@ -""" -Перечисление с типами ингредиентов. -SAUCE – соус -FILLING – начинка -""" -INGREDIENT_TYPE_SAUCE = 'SAUCE' -INGREDIENT_TYPE_FILLING = 'FILLING' diff --git a/__init__.py b/praktikum/__init__.py similarity index 100% rename from __init__.py rename to praktikum/__init__.py diff --git a/praktikum/__pycache__/__init__.cpython-313.pyc b/praktikum/__pycache__/__init__.cpython-313.pyc new file mode 100644 index 000000000..80ed887ca Binary files /dev/null and b/praktikum/__pycache__/__init__.cpython-313.pyc differ diff --git a/praktikum/__pycache__/bun.cpython-313.pyc b/praktikum/__pycache__/bun.cpython-313.pyc new file mode 100644 index 000000000..05886017f Binary files /dev/null and b/praktikum/__pycache__/bun.cpython-313.pyc differ diff --git a/praktikum/__pycache__/burger.cpython-313.pyc b/praktikum/__pycache__/burger.cpython-313.pyc new file mode 100644 index 000000000..217cda5ec Binary files /dev/null and b/praktikum/__pycache__/burger.cpython-313.pyc differ diff --git a/praktikum/__pycache__/database.cpython-313.pyc b/praktikum/__pycache__/database.cpython-313.pyc new file mode 100644 index 000000000..4ed27949b Binary files /dev/null and b/praktikum/__pycache__/database.cpython-313.pyc differ diff --git a/praktikum/__pycache__/ingredient.cpython-313.pyc b/praktikum/__pycache__/ingredient.cpython-313.pyc new file mode 100644 index 000000000..a7b69a9c0 Binary files /dev/null and b/praktikum/__pycache__/ingredient.cpython-313.pyc differ diff --git a/praktikum/__pycache__/ingredient_types.cpython-313.pyc b/praktikum/__pycache__/ingredient_types.cpython-313.pyc new file mode 100644 index 000000000..be5cce528 Binary files /dev/null and b/praktikum/__pycache__/ingredient_types.cpython-313.pyc differ diff --git a/bun.py b/praktikum/bun.py similarity index 58% rename from bun.py rename to praktikum/bun.py index 5504bc1f4..e4e844322 100644 --- a/bun.py +++ b/praktikum/bun.py @@ -1,9 +1,7 @@ class Bun: - """ - Модель булочки для бургера. - Булочке можно дать название и назначить цену. - """ - + # Модель булочки для бургера. + #Булочке можно дать название и назначить цену. + def __init__(self, name: str, price: float): self.name = name self.price = price diff --git a/burger.py b/praktikum/burger.py similarity index 78% rename from burger.py rename to praktikum/burger.py index 2b3b6a88b..863ca17a7 100644 --- a/burger.py +++ b/praktikum/burger.py @@ -5,13 +5,11 @@ class Burger: - """ - Модель бургера. - Бургер состоит из булочек и ингредиентов (начинка или соус). - Ингредиенты можно перемещать и удалять. - Можно распечать чек с информацией о бургере. - """ - + # Модель бургера. + # Бургер состоит из булочек и ингредиентов (начинка или соус). + # Ингредиенты можно перемещать и удалять. + # Можно распечать чек с информацией о бургере. + def __init__(self): self.bun = None self.ingredients: List[Ingredient] = [] diff --git a/database.py b/praktikum/database.py similarity index 91% rename from database.py rename to praktikum/database.py index 4c75baf71..08cd18182 100644 --- a/database.py +++ b/praktikum/database.py @@ -6,10 +6,8 @@ class Database: - """ - Класс с методами по работе с базой данных. - """ - + # Класс с методами по работе с базой данных. + def __init__(self): self.buns: List[Bun] = [] self.ingredients: List[Ingredient] = [] diff --git a/ingredient.py b/praktikum/ingredient.py similarity index 60% rename from ingredient.py rename to praktikum/ingredient.py index 0e50db8a2..9e9102267 100644 --- a/ingredient.py +++ b/praktikum/ingredient.py @@ -1,10 +1,8 @@ class Ingredient: - """ - Модель ингредиента. - Ингредиент: начинка или соус. - У ингредиента есть тип (начинка или соус), название и цена. - """ - + # Модель ингредиента. + #Ингредиент: начинка или соус. + #У ингредиента есть тип (начинка или соус), название и цена. + def __init__(self, ingredient_type: str, name: str, price: float): self.type = ingredient_type self.name = name diff --git a/praktikum/ingredient_types.py b/praktikum/ingredient_types.py new file mode 100644 index 000000000..df7117902 --- /dev/null +++ b/praktikum/ingredient_types.py @@ -0,0 +1,6 @@ +#Перечисление с типами ингредиентов. +#SAUCE – соус +#FILLING – начинка + +INGREDIENT_TYPE_SAUCE = 'SAUCE' +INGREDIENT_TYPE_FILLING = 'FILLING' diff --git a/requirements.txt b/requirements.txt new file mode 100644 index 000000000..cffeec658 --- /dev/null +++ b/requirements.txt @@ -0,0 +1,2 @@ +pytest +pytest-cov \ No newline at end of file diff --git a/tests/__pycache__/conftest.cpython-313-pytest-8.3.5.pyc b/tests/__pycache__/conftest.cpython-313-pytest-8.3.5.pyc new file mode 100644 index 000000000..f62802a61 Binary files /dev/null and b/tests/__pycache__/conftest.cpython-313-pytest-8.3.5.pyc differ diff --git a/tests/__pycache__/test_bun.cpython-313-pytest-8.3.5.pyc b/tests/__pycache__/test_bun.cpython-313-pytest-8.3.5.pyc new file mode 100644 index 000000000..c10854a75 Binary files /dev/null and b/tests/__pycache__/test_bun.cpython-313-pytest-8.3.5.pyc differ diff --git a/tests/__pycache__/test_burger.cpython-313-pytest-8.3.5.pyc b/tests/__pycache__/test_burger.cpython-313-pytest-8.3.5.pyc new file mode 100644 index 000000000..c9c2ba4ca Binary files /dev/null and b/tests/__pycache__/test_burger.cpython-313-pytest-8.3.5.pyc differ diff --git a/tests/__pycache__/test_database.cpython-313-pytest-8.3.5.pyc b/tests/__pycache__/test_database.cpython-313-pytest-8.3.5.pyc new file mode 100644 index 000000000..4bf647a07 Binary files /dev/null and b/tests/__pycache__/test_database.cpython-313-pytest-8.3.5.pyc differ diff --git a/tests/__pycache__/test_ingredient.cpython-313-pytest-8.3.5.pyc b/tests/__pycache__/test_ingredient.cpython-313-pytest-8.3.5.pyc new file mode 100644 index 000000000..8ecf8f8a8 Binary files /dev/null and b/tests/__pycache__/test_ingredient.cpython-313-pytest-8.3.5.pyc differ diff --git a/tests/conftest.py b/tests/conftest.py new file mode 100644 index 000000000..19d83f24b --- /dev/null +++ b/tests/conftest.py @@ -0,0 +1,18 @@ +import pytest +from praktikum.bun import Bun +from praktikum.ingredient import Ingredient + + +@pytest.fixture +def bun(): + return Bun('Флюоресцентная булка R2-D3', 988) + + +@pytest.fixture +def ingredient_main(): + return Ingredient('Начинка', 'Говяжий метеорит (отбивная)', 3000) + + +@pytest.fixture +def ingredient_sauce(): + return Ingredient('Соус', 'Соус Spicy-X', 90) \ No newline at end of file diff --git a/tests/test_bun.py b/tests/test_bun.py new file mode 100644 index 000000000..e38db8ed0 --- /dev/null +++ b/tests/test_bun.py @@ -0,0 +1,39 @@ +import pytest +from praktikum.bun import Bun + + +class TestBun: + @pytest.mark.parametrize( + 'name, price', + [ + ('Флюоресцентная булка R2-D3', 988), + ('Краторная булка N-200i', 1255), + ], + ) + def test_bun_fields(self, name, price): + bun = Bun(name, price) + + assert bun.name == name + assert bun.price == price + + @pytest.mark.parametrize( + 'name, price', + [ + ('Флюоресцентная булка R2-D3', 988), + ('Краторная булка N-200i', 1255), + ], + ) + def test_get_bun_name(self, name, price): # Проверяем метод get_name()bun = Bun(name, price) + bun = Bun(name, price) + assert bun.get_name() == name + + @pytest.mark.parametrize( + 'name, price', + [ + ('Флюоресцентная булка R2-D3', 988), + ('Краторная булка N-200i', 1255), + ], + ) + def test_get_bun_price(self, name, price): # Проверяем метод get_name()bun = Bun(name, price) + bun = Bun(name, price) + assert bun.get_price() == price \ No newline at end of file diff --git a/tests/test_burger.py b/tests/test_burger.py new file mode 100644 index 000000000..12e9f0e16 --- /dev/null +++ b/tests/test_burger.py @@ -0,0 +1,78 @@ +from unittest.mock import Mock +from praktikum.burger import Burger + +class TestBurger: + def test_set_buns_sets_bun(self, bun): + + burger = Burger() + burger.set_buns(bun) + + assert burger.bun == bun + + def test_add_ingredient_adds_item_to_list(self, ingredient_main): + + burger = Burger() + burger.add_ingredient(ingredient_main) + + assert burger.ingredients == [ingredient_main] + + def test_remove_ingredient_removes_item_by_index(self, ingredient_main, ingredient_sauce): + + burger = Burger() + burger.add_ingredient(ingredient_main) + burger.add_ingredient(ingredient_sauce) + burger.remove_ingredient(0) + + assert burger.ingredients == [ingredient_sauce] + + def test_move_ingredient_moves_item_to_new_index(self, ingredient_main, ingredient_sauce): + + second_ingredient = Mock() + second_ingredient.get_price.return_value = 100 + second_ingredient.get_name.return_value = 'Сыр с астероидной плесенью' + second_ingredient.get_type.return_value = 'Начинка' + + burger = Burger() + burger.add_ingredient(ingredient_main) + burger.add_ingredient(ingredient_sauce) + burger.add_ingredient(second_ingredient) + burger.move_ingredient(2, 0) + + assert burger.ingredients == [second_ingredient, ingredient_main, ingredient_sauce] + + def test_get_price_returns_sum_of_bun_and_ingredients_prices(self): + + bun = Mock() + bun.get_price.return_value = 100 + + ingredient_1 = Mock() + ingredient_1.get_price.return_value = 50 + + ingredient_2 = Mock() + ingredient_2.get_price.return_value = 25 + + burger = Burger() + burger.set_buns(bun) + burger.add_ingredient(ingredient_1) + burger.add_ingredient(ingredient_2) + + assert burger.get_price() == 275 + + def test_get_receipt_returns_expected_string(self): + + bun = Mock() + bun.get_name.return_value = 'Булка' + bun.get_price.return_value = 100 + + ingredient = Mock() + ingredient.get_type.return_value = 'Соус' + ingredient.get_name.return_value = 'Соус Spicy-X' + ingredient.get_price.return_value = 50 + + burger = Burger() + burger.set_buns(bun) + burger.add_ingredient(ingredient) + + expected = '(==== Булка ====)\n= соус Соус Spicy-X =\n(==== Булка ====)\n\nPrice: 250' + + assert burger.get_receipt() == expected \ No newline at end of file diff --git a/tests/test_database.py b/tests/test_database.py new file mode 100644 index 000000000..b5f7629fc --- /dev/null +++ b/tests/test_database.py @@ -0,0 +1,84 @@ +from praktikum.database import Database +from praktikum.bun import Bun +from praktikum.ingredient import Ingredient + + +class TestDatabase: + def test_available_buns_returns_non_empty_list(self): + database = Database() + buns = database.available_buns() + + assert buns + + def test_available_buns_returns_bun_objects(self): + database = Database() + buns = database.available_buns() + + assert all(isinstance(bun, Bun) for bun in buns) + + def test_available_ingredients_returns_non_empty_list(self): + database = Database() + ingredients = database.available_ingredients() + + assert ingredients + + def test_available_ingredients_returns_ingredient_objects(self): + database = Database() + ingredients = database.available_ingredients() + + assert all(isinstance(item, Ingredient) for item in ingredients) + + def test_first_bun_name_is_black_bun(self): + database = Database() + buns = database.available_buns() + + assert buns[0].get_name() == 'black bun' + + def test_first_bun_price_is_100(self): + database = Database() + buns = database.available_buns() + + assert buns[0].get_price() == 100 + + def test_second_bun_name_is_white_bun(self): + database = Database() + buns = database.available_buns() + + assert buns[1].get_name() == 'white bun' + + def test_second_bun_price_is_200(self): + database = Database() + buns = database.available_buns() + + assert buns[1].get_price() == 200 + + def test_first_ingredient_type_is_sauce(self): + database = Database() + ingredients = database.available_ingredients() + + assert ingredients[0].get_type() == 'SAUCE' + + def test_first_ingredient_name_is_hot_sauce(self): + database = Database() + ingredients = database.available_ingredients() + + assert ingredients[0].get_name() == 'hot sauce' + + def test_first_ingredient_price_is_100(self): + database = Database() + ingredients = database.available_ingredients() + + assert ingredients[0].get_price() == 100 + + def test_last_ingredient_type_is_filling(self): + database = Database() + ingredients = database.available_ingredients() + + assert ingredients[-1].get_type() == 'FILLING' + + def test_last_ingredient_name_is_sausage(self): + database = Database() + ingredients = database.available_ingredients() + + assert ingredients[-1].get_name() == 'sausage' + diff --git a/tests/test_ingredient.py b/tests/test_ingredient.py new file mode 100644 index 000000000..ca9f10b4b --- /dev/null +++ b/tests/test_ingredient.py @@ -0,0 +1,76 @@ +import pytest +from praktikum.ingredient import Ingredient + + +class TestIngredient: + @pytest.mark.parametrize( + 'type_, name, price', + [ + ('Соус', 'Соус Spicy-X', 90), + ('Начинка', 'Говяжий метеорит (отбивная)', 3000), + ], + ) + def test_ingredient_type_field_is_set_correctly(self, type_, name, price): + ingredient = Ingredient(type_, name, price) + + assert ingredient.type == type_ + + @pytest.mark.parametrize( + 'type_, name, price', + [ + ('Соус', 'Соус Spicy-X', 90), + ('Начинка', 'Говяжий метеорит (отбивная)', 3000), + ], + ) + def test_ingredient_name_field_is_set_correctly(self, type_, name, price): + ingredient = Ingredient(type_, name, price) + + assert ingredient.name == name + + @pytest.mark.parametrize( + 'type_, name, price', + [ + ('Соус', 'Соус Spicy-X', 90), + ('Начинка', 'Говяжий метеорит (отбивная)', 3000), + ], + ) + def test_ingredient_price_field_is_set_correctly(self, type_, name, price): + ingredient = Ingredient(type_, name, price) + + assert ingredient.price == price + + @pytest.mark.parametrize( + 'type_, name, price', + [ + ('Соус', 'Соус Spicy-X', 90), + ('Начинка', 'Говяжий метеорит (отбивная)', 3000), + ], + ) + def test_get_type_returns_correct_value(self, type_, name, price): + ingredient = Ingredient(type_, name, price) + + assert ingredient.get_type() == type_ + + @pytest.mark.parametrize( + 'type_, name, price', + [ + ('Соус', 'Соус Spicy-X', 90), + ('Начинка', 'Говяжий метеорит (отбивная)', 3000), + ], + ) + def test_get_name_returns_correct_value(self, type_, name, price): + ingredient = Ingredient(type_, name, price) + + assert ingredient.get_name() == name + + @pytest.mark.parametrize( + 'type_, name, price', + [ + ('Соус', 'Соус Spicy-X', 90), + ('Начинка', 'Говяжий метеорит (отбивная)', 3000), + ], + ) + def test_get_price_returns_correct_value(self, type_, name, price): + ingredient = Ingredient(type_, name, price) + + assert ingredient.get_price() == price \ No newline at end of file