Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

patterns v1 #612

Open
wants to merge 1 commit into
base: Ppozhidaev/master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 8 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
composer.phar
/code/vendor
/app
/.idea/
/db*/
/*.env
/app/public/logs
/rabbitmq
48 changes: 47 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
@@ -1 +1,47 @@
# PHP_2022
# PHP_2022
### Design Patterns

---
##### Описание
- Фабричный метод - (Products) - генерирует заказанный продукт
- Цепочка обязанностей - Операции(Actions) - добавляют ингредиенты согласно рецепту и пожеланиям заказчика
- Стратегия - Рецепты(Recipes) - определяет порядок приготовления
- Наблюдатель - Монитор в зале(HallDisplay) - выводит статус приготовления
- Прокси - (KitchenWithQualityControl) - расширяет класс Kitchen, добавляет функционал проверки качества продукта


###### Порядок запуска
Установить необходимые пакеты§
```bash
composer install
```
Собрать и запустить докер
```bash
docker compose up -d --build
```

Запустить в консоли обработчик запросов
```bash
docker exec -it fast-food sh
```

Сделать заказ
```bash
php app.php -p burger
```
Сделать заказ и убрать ингредиенты
```bash
php app.php -p burger -e onion
```

---
##### Задание
Разрабатываем часть интернет-ресторана. Продаёт он фаст-фуд.

1. Фабричный метод будет отвечать за генерацию базового продукта-прототипа, из которого будут готовиться: бургер, сэндвич или хот-дог
2. При готовке каждого типа продукта Цепочка обязанностей будет добавлять составляющие к базовому продукту либо по рецепту, либо по пожеланию клиента (салат, лук, перец и т.д.)
3. Наблюдатель подписывается на статус приготовления и отправляет оповещения о том, что изменился статус приготовления продукта.
4. Прокси используется для навешивания пре и пост событий на процесс готовки. Например, если бургер не соответствует стандарту, пост событие утилизирует его.
5. Стратегия будет отвечать за то, что нужно приготовить.

Все сущности должны по максимуму генерироваться через DI.
12 changes: 12 additions & 0 deletions code/app.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
<?php
require_once __DIR__."/vendor/autoload.php";

use Ppro\Hw20\Application\App;

try {
$app = new App();
$app->run();
}
catch(\Exception $e){
echo $e->getMessage();
}
13 changes: 13 additions & 0 deletions code/composer.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
{
"name": "ppro/hw20",
"autoload": {
"psr-4": {
"Ppro\\Hw20\\": "src/"
}
},
"config": {
"platform": {
"php": "8.1"
}
}
}
21 changes: 21 additions & 0 deletions code/composer.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

19 changes: 19 additions & 0 deletions code/src/Actions/Add.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
<?php

namespace Ppro\Hw20\Actions;

use Ppro\Hw20\Exceptions\AppException;
use Ppro\Hw20\Products\ProductFactoryInterface;
use Ppro\Hw20\Products\ProductInterface;

/** Добавляем игредиент в готовое блюдо
*
*/
class Add extends CookAction
{
public function handle(ProductInterface $product): void
{
$product->getProductObject()->setFinishedProduct(array_merge($product->getProductObject()->getFinishedProduct(),$this->ingredient));
parent::handle($product);
}
}
26 changes: 26 additions & 0 deletions code/src/Actions/CookAction.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
<?php

namespace Ppro\Hw20\Actions;

use Ppro\Hw20\Products\ProductInterface;
use Ppro\Hw20\Recipes\RecipeStrategyInterface;

abstract class CookAction
{
public function __construct(protected ?array $ingredient = null,protected ?RecipeStrategyInterface $recipe = null, private ?CookAction $nextAction = null)
{
}

public function setNextAction(CookAction $action): CookAction
{
$this->nextAction = $action;
return $action;
}

public function handle(ProductInterface $product): void
{
if ($this->nextAction !== null) {
$this->nextAction->handle($product);
}
}
}
18 changes: 18 additions & 0 deletions code/src/Actions/Fry.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
<?php

namespace Ppro\Hw20\Actions;

use Ppro\Hw20\Products\ProductInterface;

/** Жарим и добавляем игредиент в готовое блюдо
*
*/
class Fry extends CookAction
{
public function handle(ProductInterface $product): void
{
array_walk($this->ingredient,fn(&$ingredient,$key,$operation):string => $ingredient = $operation.$ingredient,'Fried ');
$product->getProductObject()->setFinishedProduct(array_merge($product->getProductObject()->getFinishedProduct(),$this->ingredient));
parent::handle($product);
}
}
26 changes: 26 additions & 0 deletions code/src/Actions/Prepare.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
<?php

namespace Ppro\Hw20\Actions;

use Ppro\Hw20\Exceptions\KitchenException;
use Ppro\Hw20\Products\ProductInterface;

/** Проверяем наличие ингредиентов на складе
*
*/
class Prepare extends CookAction
{
public function handle(ProductInterface $product): void
{
$this->checkIngredientsAvailability($this->ingredient);
parent::handle($product);
}

private function checkIngredientsAvailability(array $ingredients)
{
//... проверка наличия ингредиентов
$available = true;
if(!$available)
throw new KitchenException("Ingredient does not exist");
}
}
63 changes: 63 additions & 0 deletions code/src/Application/App.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,63 @@
<?php

namespace Ppro\Hw20\Application;

use Ppro\Hw20\Exceptions\AppException;
use Ppro\Hw20\Services\Order;

class App
{
/**
* @var Register|null
*/
private ?Register $reg;

/**
*
*/
public function __construct()
{
$this->reg = Register::instance();
}

/**
* @return void
* @throws AppException
*/
public function run()
{
$this->init();
$this->handleRequest();
}

/**
* @return void
*/
private function init()
{
$this->reg->getApplicationHelper()->init();
}

/**
* @return void
* @throws AppException
*/
private function handleRequest()
{
$orderCmd = ($this->reg->getRequest())->getOrder();
if(empty($orderCmd))
throw new AppException('Command is empty');
$orderSets = ($this->reg->getRequest())->getSets();
$recipeClass = Register::instance()->getRecipe($orderCmd);
$productClass = Register::instance()->getProduct($orderCmd);
$recipeSteps = Register::instance()->getRecipeSteps()->getAll()[$orderCmd] ?? [];

$order = new Order();
$order->make($recipeClass, $productClass, $recipeSteps, $orderSets);
}





}
59 changes: 59 additions & 0 deletions code/src/Application/ApplicationHelper.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,59 @@
<?php
declare(strict_types = 1);

namespace Ppro\Hw20\Application;

use Ppro\Hw20\Application\Conf;
use Ppro\Hw20\Application\Register;
use Ppro\Hw20\Application\Request;

class ApplicationHelper
{
/**
* @var string
*/
private $config = __DIR__ . "/../Config/options.ini";
private $recipesConfig = __DIR__ . "/../Config/recipes.ini";

private $reg;

public function __construct()
{
$this->reg = Register::instance();
}

public function init()
{
$this->setupOptions();

$request = Request::getInstance();
$this->reg->setRequest($request);
}

/** Обработка конфигурационных файлов приложения
* @return void
* @throws AppException
*/
private function setupOptions()
{
if (! file_exists($this->config)) {
throw new AppException("Could not find options file");
}

$options = parse_ini_file($this->config, true);
$recipe = new Conf($options['recipe']);

$this->reg->setRecipes($recipe);
$product = new Conf($options['product']);
$this->reg->setProducts($product);

if (! file_exists($this->recipesConfig)) {
throw new AppException("Could not find recipes file");
}

$recipesConfigArray = parse_ini_file($this->recipesConfig, true);
$recipeSteps = new Conf($recipesConfigArray);
$this->reg->setRecipeSteps($recipeSteps);

}
}
32 changes: 32 additions & 0 deletions code/src/Application/Conf.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
<?php
declare(strict_types = 1);

namespace Ppro\Hw20\Application;

class Conf
{
private $vals = [];

public function __construct(array $vals = [])
{
$this->vals = $vals;
}

public function get(string $key)
{
if (isset($this->vals[$key])) {
return $this->vals[$key];
}
return null;
}

public function set(string $key, $val)
{
$this->vals[$key] = $val;
}

public function getAll(): array
{
return $this->vals;
}
}
Loading