This commit is contained in:
lubiana 2025-06-08 19:25:02 +02:00
parent b052697417
commit 43ca79f650
Signed by: lubiana
SSH key fingerprint: SHA256:vW1EA0fRR3Fw+dD/sM0K+x3Il2gSry6YRYHqOeQwrfk
14 changed files with 292 additions and 57 deletions

View file

@ -28,7 +28,7 @@ final class DrinkTypeController extends AbstractController
#[Route(path: '/new', name: 'app_drink_type_new', methods: ['GET', 'POST'])] #[Route(path: '/new', name: 'app_drink_type_new', methods: ['GET', 'POST'])]
public function new(Request $request, EntityManagerInterface $entityManager): Response public function new(Request $request, EntityManagerInterface $entityManager): Response
{ {
$drinkType = new DrinkType('', ''); $drinkType = new DrinkType();
$form = $this->createForm(DrinkTypeForm::class, $drinkType); $form = $this->createForm(DrinkTypeForm::class, $drinkType);
$form->handleRequest($request); $form->handleRequest($request);

View file

@ -0,0 +1,81 @@
<?php
namespace App\Controller;
use App\Entity\InventoryRecord;
use App\Form\InventoryRecordForm;
use App\Repository\InventoryRecordRepository;
use Doctrine\ORM\EntityManagerInterface;
use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\HttpFoundation\Response;
use Symfony\Component\Routing\Attribute\Route;
#[Route('/inventory-record')]
final class InventoryRecordController extends AbstractController
{
#[Route(name: 'app_inventory_record_index', methods: ['GET'])]
public function index(InventoryRecordRepository $inventoryRecordRepository): Response
{
return $this->render('inventory_record/index.html.twig', [
'inventory_records' => $inventoryRecordRepository->findAll(),
]);
}
#[Route('/new', name: 'app_inventory_record_new', methods: ['GET', 'POST'])]
public function new(Request $request, EntityManagerInterface $entityManager): Response
{
$inventoryRecord = new InventoryRecord();
$form = $this->createForm(InventoryRecordForm::class, $inventoryRecord);
$form->handleRequest($request);
if ($form->isSubmitted() && $form->isValid()) {
$entityManager->persist($inventoryRecord);
$entityManager->flush();
return $this->redirectToRoute('app_inventory_record_index', [], Response::HTTP_SEE_OTHER);
}
return $this->render('inventory_record/new.html.twig', [
'inventory_record' => $inventoryRecord,
'form' => $form,
]);
}
#[Route('/{id}', name: 'app_inventory_record_show', methods: ['GET'])]
public function show(InventoryRecord $inventoryRecord): Response
{
return $this->render('inventory_record/show.html.twig', [
'inventory_record' => $inventoryRecord,
]);
}
#[Route('/{id}/edit', name: 'app_inventory_record_edit', methods: ['GET', 'POST'])]
public function edit(Request $request, InventoryRecord $inventoryRecord, EntityManagerInterface $entityManager): Response
{
$form = $this->createForm(InventoryRecordForm::class, $inventoryRecord);
$form->handleRequest($request);
if ($form->isSubmitted() && $form->isValid()) {
$entityManager->flush();
return $this->redirectToRoute('app_inventory_record_index', [], Response::HTTP_SEE_OTHER);
}
return $this->render('inventory_record/edit.html.twig', [
'inventory_record' => $inventoryRecord,
'form' => $form,
]);
}
#[Route('/{id}', name: 'app_inventory_record_delete', methods: ['POST'])]
public function delete(Request $request, InventoryRecord $inventoryRecord, EntityManagerInterface $entityManager): Response
{
if ($this->isCsrfTokenValid('delete'.$inventoryRecord->getId(), $request->getPayload()->getString('_token'))) {
$entityManager->remove($inventoryRecord);
$entityManager->flush();
}
return $this->redirectToRoute('app_inventory_record_index', [], Response::HTTP_SEE_OTHER);
}
}

View file

@ -31,18 +31,17 @@ class DrinkType
#[ORM\OneToMany(mappedBy: 'drinkType', targetEntity: OrderItem::class)] #[ORM\OneToMany(mappedBy: 'drinkType', targetEntity: OrderItem::class)]
private Collection $orderItems; private Collection $orderItems;
public function __construct(
#[ORM\Column(type: 'string', length: 255, unique: true)] #[ORM\Column(type: 'string', length: 255, unique: true)]
private string $name, private string $name;
#[ORM\Column(type: 'text', nullable: true)] #[ORM\Column(type: 'text', nullable: true)]
private null|string $description = null, private null|string $description = null;
#[ORM\Column(type: 'integer')] #[ORM\Column(type: 'integer')]
private int $desiredStock = 10, private int $desiredStock = 10;
null|DateTimeImmutable $createdAt = null,
null|DateTimeImmutable $updatedAt = null, public function __construct(
) { ) {
$this->createdAt = $createdAt ?? new DateTimeImmutable(); $this->createdAt = new DateTimeImmutable();
$this->updatedAt = $updatedAt ?? new DateTimeImmutable(); $this->updatedAt = new DateTimeImmutable();
$this->inventoryRecords = new ArrayCollection(); $this->inventoryRecords = new ArrayCollection();
$this->orderItems = new ArrayCollection(); $this->orderItems = new ArrayCollection();
} }

View file

@ -17,19 +17,28 @@ class InventoryRecord
#[ORM\Column(type: 'integer')] #[ORM\Column(type: 'integer')]
private null|int $id = null; private null|int $id = null;
public function __construct(
#[ORM\ManyToOne(targetEntity: DrinkType::class, inversedBy: 'inventoryRecords')] #[ORM\ManyToOne(targetEntity: DrinkType::class, inversedBy: 'inventoryRecords')]
#[ORM\JoinColumn(name: 'drink_type_id', referencedColumnName: 'id', nullable: false)] #[ORM\JoinColumn(name: 'drink_type_id', referencedColumnName: 'id', nullable: false)]
private DrinkType $drinkType, private DrinkType $drinkType;
#[ORM\Column(type: 'integer')] #[ORM\Column(type: 'integer')]
private int $quantity, private int $quantity;
#[ORM\Column(type: 'datetime_immutable')] #[ORM\Column(type: 'datetime_immutable')]
private DateTimeImmutable $timestamp = new DateTimeImmutable(), private DateTimeImmutable $timestamp;
#[ORM\Column(type: 'datetime_immutable')] #[ORM\Column(type: 'datetime_immutable')]
private DateTimeImmutable $createdAt = new DateTimeImmutable(), private DateTimeImmutable $createdAt;
#[ORM\Column(type: 'datetime_immutable')] #[ORM\Column(type: 'datetime_immutable')]
private DateTimeImmutable $updatedAt = new DateTimeImmutable(), private DateTimeImmutable $updatedAt;
) {}
public function __construct(
) {
$this->createdAt = new DateTimeImmutable();
$this->updatedAt = new DateTimeImmutable();
$this->timestamp = new DateTimeImmutable();
}
public function getId(): null|int public function getId(): null|int
{ {

View file

@ -29,16 +29,15 @@ class Order
#[ORM\OneToMany(mappedBy: 'order', targetEntity: OrderItem::class, cascade: ['persist', 'remove'])] #[ORM\OneToMany(mappedBy: 'order', targetEntity: OrderItem::class, cascade: ['persist', 'remove'])]
private Collection $orderItems; private Collection $orderItems;
public function __construct(
#[ORM\Column(nullable: false, enumType: OrderStatus::class, options: [ #[ORM\Column(nullable: false, enumType: OrderStatus::class, options: [
'default' => OrderStatus::NEW, 'default' => OrderStatus::NEW,
])] ])]
private OrderStatus $status = OrderStatus::NEW, private OrderStatus $status = OrderStatus::NEW;
null|DateTimeImmutable $createdAt = null,
null|DateTimeImmutable $updatedAt = null, public function __construct(
) { ) {
$this->createdAt = $createdAt ?? new DateTimeImmutable(); $this->createdAt = new DateTimeImmutable();
$this->updatedAt = $updatedAt ?? new DateTimeImmutable(); $this->updatedAt = new DateTimeImmutable();
$this->orderItems = new ArrayCollection(); $this->orderItems = new ArrayCollection();
} }

View file

@ -23,25 +23,21 @@ class OrderItem
#[ORM\Column(type: 'datetime_immutable')] #[ORM\Column(type: 'datetime_immutable')]
private DateTimeImmutable $updatedAt; private DateTimeImmutable $updatedAt;
public function __construct(
#[ORM\ManyToOne(targetEntity: DrinkType::class, inversedBy: 'orderItems')] #[ORM\ManyToOne(targetEntity: DrinkType::class, inversedBy: 'orderItems')]
#[ORM\JoinColumn(name: 'drink_type_id', referencedColumnName: 'id', nullable: false)] #[ORM\JoinColumn(name: 'drink_type_id', referencedColumnName: 'id', nullable: false)]
private DrinkType $drinkType, private DrinkType $drinkType;
#[ORM\Column(type: 'integer')] #[ORM\Column(type: 'integer')]
private int $quantity, private int $quantity;
#[ORM\ManyToOne(targetEntity: Order::class, inversedBy: 'orderItems')] #[ORM\ManyToOne(targetEntity: Order::class, inversedBy: 'orderItems')]
#[ORM\JoinColumn(name: 'order_id', referencedColumnName: 'id', nullable: false)] #[ORM\JoinColumn(name: 'order_id', referencedColumnName: 'id', nullable: false)]
private null|Order $order = null, private Order $order;
null|DateTimeImmutable $createdAt = null,
null|DateTimeImmutable $updatedAt = null,
) {
$this->createdAt = $createdAt ?? new DateTimeImmutable();
$this->updatedAt = $updatedAt ?? new DateTimeImmutable();
// Establish bidirectional relationship public function __construct(
if ($this->order instanceof Order) { ) {
$this->order->addOrderItem($this); $this->createdAt = new DateTimeImmutable();
} $this->updatedAt = new DateTimeImmutable();
} }
public function getId(): null|int public function getId(): null|int

View file

@ -31,16 +31,16 @@ class SystemConfig
#[ORM\Column(type: 'datetime_immutable')] #[ORM\Column(type: 'datetime_immutable')]
private DateTimeImmutable $updatedAt; private DateTimeImmutable $updatedAt;
public function __construct(
#[ORM\Column(unique: true, enumType: SystemSettingKey::class)] #[ORM\Column(unique: true, enumType: SystemSettingKey::class)]
private SystemSettingKey $key, private SystemSettingKey $key;
#[ORM\Column(type: 'text')] #[ORM\Column(type: 'text')]
private string $value, private string $value;
null|DateTimeImmutable $createdAt = null,
null|DateTimeImmutable $updatedAt = null, public function __construct(
) { ) {
$this->createdAt = $createdAt ?? new DateTimeImmutable(); $this->createdAt = new DateTimeImmutable();
$this->updatedAt = $updatedAt ?? new DateTimeImmutable(); $this->updatedAt = new DateTimeImmutable();
} }
public function getId(): null|int public function getId(): null|int

View file

@ -0,0 +1,40 @@
<?php
namespace App\Form;
use App\Entity\DrinkType;
use App\Entity\InventoryRecord;
use Symfony\Bridge\Doctrine\Form\Type\EntityType;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolver;
class InventoryRecordForm extends AbstractType
{
public function buildForm(FormBuilderInterface $builder, array $options): void
{
$builder
->add('quantity')
->add('timestamp', null, [
'widget' => 'single_text',
])
->add('createdAt', null, [
'widget' => 'single_text',
])
->add('updatedAt', null, [
'widget' => 'single_text',
])
->add('drinkType', EntityType::class, [
'class' => DrinkType::class,
'choice_label' => 'id',
])
;
}
public function configureOptions(OptionsResolver $resolver): void
{
$resolver->setDefaults([
'data_class' => InventoryRecord::class,
]);
}
}

View file

@ -0,0 +1,4 @@
<form method="post" action="{{ path('app_inventory_record_delete', {'id': inventory_record.id}) }}" onsubmit="return confirm('Are you sure you want to delete this item?');">
<input type="hidden" name="_token" value="{{ csrf_token('delete' ~ inventory_record.id) }}">
<button class="btn">Delete</button>
</form>

View file

@ -0,0 +1,4 @@
{{ form_start(form) }}
{{ form_widget(form) }}
<button class="btn">{{ button_label|default('Save') }}</button>
{{ form_end(form) }}

View file

@ -0,0 +1,13 @@
{% extends 'base.html.twig' %}
{% block title %}Edit InventoryRecord{% endblock %}
{% block body %}
<h1>Edit InventoryRecord</h1>
{{ include('inventory_record/_form.html.twig', {'button_label': 'Update'}) }}
<a href="{{ path('app_inventory_record_index') }}">back to list</a>
{{ include('inventory_record/_delete_form.html.twig') }}
{% endblock %}

View file

@ -0,0 +1,41 @@
{% extends 'base.html.twig' %}
{% block title %}InventoryRecord index{% endblock %}
{% block body %}
<h1>InventoryRecord index</h1>
<table class="table">
<thead>
<tr>
<th>Id</th>
<th>Quantity</th>
<th>Timestamp</th>
<th>CreatedAt</th>
<th>UpdatedAt</th>
<th>actions</th>
</tr>
</thead>
<tbody>
{% for inventory_record in inventory_records %}
<tr>
<td>{{ inventory_record.id }}</td>
<td>{{ inventory_record.quantity }}</td>
<td>{{ inventory_record.timestamp ? inventory_record.timestamp|date('Y-m-d H:i:s') : '' }}</td>
<td>{{ inventory_record.createdAt ? inventory_record.createdAt|date('Y-m-d H:i:s') : '' }}</td>
<td>{{ inventory_record.updatedAt ? inventory_record.updatedAt|date('Y-m-d H:i:s') : '' }}</td>
<td>
<a href="{{ path('app_inventory_record_show', {'id': inventory_record.id}) }}">show</a>
<a href="{{ path('app_inventory_record_edit', {'id': inventory_record.id}) }}">edit</a>
</td>
</tr>
{% else %}
<tr>
<td colspan="6">no records found</td>
</tr>
{% endfor %}
</tbody>
</table>
<a href="{{ path('app_inventory_record_new') }}">Create new</a>
{% endblock %}

View file

@ -0,0 +1,11 @@
{% extends 'base.html.twig' %}
{% block title %}New InventoryRecord{% endblock %}
{% block body %}
<h1>Create new InventoryRecord</h1>
{{ include('inventory_record/_form.html.twig') }}
<a href="{{ path('app_inventory_record_index') }}">back to list</a>
{% endblock %}

View file

@ -0,0 +1,38 @@
{% extends 'base.html.twig' %}
{% block title %}InventoryRecord{% endblock %}
{% block body %}
<h1>InventoryRecord</h1>
<table class="table">
<tbody>
<tr>
<th>Id</th>
<td>{{ inventory_record.id }}</td>
</tr>
<tr>
<th>Quantity</th>
<td>{{ inventory_record.quantity }}</td>
</tr>
<tr>
<th>Timestamp</th>
<td>{{ inventory_record.timestamp ? inventory_record.timestamp|date('Y-m-d H:i:s') : '' }}</td>
</tr>
<tr>
<th>CreatedAt</th>
<td>{{ inventory_record.createdAt ? inventory_record.createdAt|date('Y-m-d H:i:s') : '' }}</td>
</tr>
<tr>
<th>UpdatedAt</th>
<td>{{ inventory_record.updatedAt ? inventory_record.updatedAt|date('Y-m-d H:i:s') : '' }}</td>
</tr>
</tbody>
</table>
<a href="{{ path('app_inventory_record_index') }}">back to list</a>
<a href="{{ path('app_inventory_record_edit', {'id': inventory_record.id}) }}">edit</a>
{{ include('inventory_record/_delete_form.html.twig') }}
{% endblock %}