Last active
April 28, 2023 10:12
-
-
Save ArtemioVegas/ccf9c9c1e6de7bab726a19c3cf791830 to your computer and use it in GitHub Desktop.
Модификация списка товаров
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
final class Cart | |
{ | |
private array $items = []; | |
public function getItems(): array | |
{ | |
// some code | |
} | |
public function getItemsCount(): int | |
{ | |
// some code | |
} | |
public function addItem($item): void | |
{ | |
// some code | |
} | |
public function deleteItem($item): void | |
{ | |
// some code | |
} | |
public function calculateTotalSum(): int | |
{ | |
// some code | |
} | |
} | |
final class OrderRepository | |
{ | |
public function load(){/*...*/ } | |
public function save(){/*...*/ } | |
public function update(){/*...*/ } | |
public function delete(){/*...*/ } | |
} | |
final class OrderView | |
{ | |
public function printOrder(){/*...*/ } | |
public function showOrder(){/*...*/ } | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/// COMPOSER | |
1) клонируем репозиторий библиотеки через git | |
2) создаем ветку в в репозитории библиотеки, в нее коммитим нужные нам доработки, например "my-feature" | |
3) Пушим ветку на сервер | |
4) в проекте создаем новую ветку от мастера, в файле composer.json меняем версию пакета на названия ветки которую пушили в либу,с префиксом "dev" например - "dev-my-feature" | |
5) обновляем билиотеку в нашем проекте - composer update test-vendor/test-library | |
6) Локально на проекте запускаем тесты, чтобы проверить что ничего не поломалось | |
7) После того как наши изменения для библиотеки влиты мейнтенером, подтягиваем обновленный пакет через composer composer update test-vendor/test-library | |
предварительно указав корректные constraint (возможно был мажорный апдейт) | |
7) После того как изменения на проекте успешно протестировано, мерджим ветку проекта в мастер | |
8) в гитлабе создаем новый тэг от свежего мастера, выкатываем его на прод |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
version: '3' | |
services: | |
db: | |
image: mysql:8 |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
version: '3' | |
networks: | |
nginx-php-network: | |
services: | |
nginx: | |
image: nginx:alpine | |
container_name: app-nginx | |
ports: | |
- "8090:8090" | |
- "443:443" | |
volumes: | |
- ./:/var/www | |
- .docker/nginx/default.conf:/etc/nginx/conf.d/default.conf | |
networks: | |
- nginx-php-network | |
links: | |
- php-fpm | |
php-fpm: | |
image: php:8.2-fpm | |
container_name: app-php | |
ports: | |
- "9000:9000" | |
volumes: | |
- ./app:/var/www/project | |
networks: | |
- nginx-php-network | |
links: | |
- db | |
db: | |
platform: linux/x86_64 | |
image: mysql:5.6.47 | |
container_name: app-db | |
ports: | |
- "3306:3306" | |
volumes: | |
- ./etc/infrastructure/mysql/my.cnf:/etc/mysql/my.cnf | |
- ./etc/database/base.sql:/docker-entrypoint-initdb.d/base.sql | |
networks: | |
- nginx-php-network |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
– предоставить авторизованному пользователю возможность добавлять продукты в избранное | |
/products/favorite метод POST | |
{ | |
"productId" : 1 | |
} | |
Пример ответа | |
HTTP/1.1 200 OK | |
- пользователь так же должен иметь возможность просматривать список избранных продуктов отдельно | |
/products/favorite метод GET | |
Пример Ответа от сервера | |
[ | |
{ | |
"id": 1, | |
"name": "Example product 1", | |
"image_url": "https://cdn.market.com/images/products/product_1.png", | |
}, | |
{ | |
"id": 4, | |
"name": "Example product 4", | |
"image_url": "https://cdn.market.com/images/products/product_4.png", | |
}, | |
] | |
- избранные продукты должны отображаться с соответствующей пометкой в общем списке всех продуктов | |
(добавляем новое свойство "isFavorite" тип boolean), | |
а так же добавляем возможность отображать массив картинок для товара | |
GET /products?category=category-1&sort=name HTTP/1.1 | |
Пример Ответа от сервера | |
[ | |
{ | |
"id": 1, | |
"name": "Example product 1", | |
"description": "Example product 1 description", | |
"image_url": "https://cdn.market.com/images/products/product_1.png", | |
"category": "category-1", | |
"isFavorite": true, | |
"image_list": [ | |
"https://cdn.market.com/images/products/product_1.png", | |
"https://aws-s3.com.com/images/products/product_5.png", | |
"https://aws-s3.com/images/products/product_6.png" | |
] | |
}, | |
{ | |
"id": 4, | |
"name": "Example product 4", | |
"description": "Example product 4 description", | |
"image_url": "https://cdn.market.com/images/products/product_4.png", | |
"category": "category-1", | |
"isFavorite": false, | |
"image_list": [ | |
"https://cdn.market.com/images/products/product_4.png", | |
"https://aws-s3.com.com/images/products/product_7.png", | |
"https://aws-s3.com/images/products/product_8.png" | |
] | |
} | |
] |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
interface StorageRepositoryInterface | |
{ | |
public function getUrl(string $fileName): ?string; | |
} | |
final class AwsStorageConcrete implements AwsStorageInterface | |
{ | |
///// | |
} | |
final class FileCommonStorageRepository implements StorageRepositoryInterface | |
{ | |
private FileStorageRepository $fileStorageRepository; | |
public function __construct(FileStorageRepository $fileStorageRepository) | |
{ | |
$this->fileStorageRepository = $fileStorageRepository; | |
} | |
public function getUrl(string $fileName): ?string | |
{ | |
$result = $this->fileStorageRepository->getImageUrl($fileName); | |
return $result; | |
} | |
} | |
// насколько я понял из текста задания, у приведенной библиотеки для работы с aws, нет метода проверка существования файла... | |
final class AwsStorageRepository implements StorageRepositoryInterface | |
{ | |
private AwsStorageInterface $awsStorageInterface; | |
private LoggerInterface $logger; | |
public function __construct( | |
AwsStorageInterface $awsStorageInterface, | |
LoggerInterface $logger | |
){ | |
$this->awsStorageInterface = $awsStorageInterface; | |
} | |
public function getUrl(string $fileName): ?string | |
{ | |
try { | |
$response = $this->awsStorageInterface->getUrl($fileName); | |
$result = (string) $response; | |
} catch (Throwable $t) { | |
$result = null; | |
$this->logger->warning('Failed to get file from AWS. Error message: '. $t->getMessage()); | |
} | |
return $result; | |
} | |
} | |
final class StorageRepositoryChain | |
{ | |
/** @var StorageRepositoryInterface[] */ | |
private array $repositories; | |
public function addRepository(StorageRepositoryInterface $repository): void | |
{ | |
$this->repositories[$repository::class] = $repository; | |
} | |
public function getUrl(string $fileName): ?string | |
{ | |
foreach ($this->repositories as $repository) { | |
$url = $repository->getUrl($fileName); | |
if (null !== $url) { | |
return $url; | |
} | |
} | |
return null; | |
} | |
} | |
// namespace Market; | |
class Product | |
{ | |
/** | |
* @var string | |
*/ | |
private string $imageFileName; | |
/** @var string[] */ | |
private array $newImages = []; | |
public function __construct(StorageRepositoryChain $chain) | |
{ | |
$this->chain = $chain; | |
} | |
public function getImageList(): array | |
{ | |
return array_merge([$this->imageFileName], $this->newImages); | |
} | |
} | |
// namespace Market; | |
class ProductImageService | |
{ | |
private StorageRepositoryChain $chain; | |
public function __construct(StorageRepositoryChain $chain) | |
{ | |
$this->chain = $chain; | |
} | |
public function getImageListForProduct(Product $product): array | |
{ | |
$result = []; | |
foreach ($product->getImageList() as $fileName) { | |
$url = $this->chain->getUrl($fileName); | |
if (null === $url) { | |
continue; | |
} | |
$result[] = $url; | |
} | |
return $result; | |
} | |
} | |
// client code | |
$chain = new StorageRepositoryChain(); | |
$chain->addRepository(new FileCommonStorageRepository(new FileStorageRepository())); | |
$chain->addRepository(new AwsStorageRepository( | |
new AwsStorageConcrete(), | |
new Logger() | |
)); | |
$productImageService = new ProductImageService($chain); | |
$productImageList = $productImageService->getImageListForProduct($product); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Тестирование | |
1) написать юнит тест, что в новый метод "getImageList" у класса Product возвращает и старые и новые имена файлов | |
2) написать юнит тест на класс AwsStorageRepository, кейсы - если файл получен | если файл не может получить | |
3) написать юнит тест на класс FileCommonStorageRepository, кейсы - если файл получен | если файл не может получить | |
4) написать юнит тест на класс StorageRepositoryChain, репозиторий вернул url | репозиторий не вернул url | |
5) написать юнит тест на класс ProductImageService, метод getImageListForProduct, замокав ответ от StorageRepositoryChain нашими данными |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
-- SQL: Оценки студентов | |
SELECT m.name, m.mark, | |
CASE | |
WHEN g.grade < 8 THEN 'low' | |
ELSE g.grade | |
END AS grade | |
FROM marks AS m | |
INNER JOIN grade AS g ON m.mark BETWEEN g.min_mark AND g.max_mark | |
ORDER BY g.grade DESC, | |
CASE WHEN g.grade BETWEEN 8 AND 10 THEN m.name END ASC, | |
CASE WHEN g.grade BETWEEN 1 AND 7 THEN m.mark END ASC | |
---- B. Модификация DDL | |
Можно попробовать поле grade добавить в таблицу marks, вычисляя его значение перед вставкой в таблицу. | |
Чтобы не делать каждый раз join при запросах, руководуствуясь логикой что операций чтения намного чаще происходят чем вставки новых записей. |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
declare(strict_types=1); | |
interface TicketRepositoryInterface | |
{ | |
public function load($ticketID): Ticket; | |
public function save($ticket): void; | |
public function update($ticket): void; | |
public function delete($ticket): void; | |
} | |
final class TicketDatabaseRepository implements TicketRepositoryInterface | |
{ | |
public function __construct(private DbConnection $connection) | |
{ | |
} | |
public function load($ticketID): Ticket | |
{ | |
// получаем данные из БД | |
} | |
public function save($ticket): void | |
{ | |
// сохраняем билет в БД | |
} | |
public function update($ticket): void | |
{ | |
// обновляем билет в БД | |
} | |
public function delete($ticket): void | |
{ | |
// удаляем билет в БД | |
} | |
} | |
final class TicketApiRepository implements TicketRepositoryInterface | |
{ | |
public function __construct(private ApiClient $client) | |
{ | |
} | |
public function load($ticketID): Ticket | |
{ | |
// посылаем запрос в API на получение билета | |
} | |
public function save($ticket): void | |
{ | |
// посылаем запрос в API на сохранение билета | |
} | |
public function update($ticket): void | |
{ | |
// посылаем запрос в API на обновление билета | |
} | |
public function delete($ticket): void | |
{ | |
// посылаем запрос в API на удаление билета | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment