feat(order/flow): Ajoute le formulaire de détails de commande.

Ajoute un formulaire Twig pour la saisie des détails de la
commande et des informations de contact.
This commit is contained in:
Serreau Jovann
2025-11-04 20:21:39 +01:00
parent 6c61ae2b1b
commit 9a3944a7a0
11 changed files with 1107 additions and 4 deletions

View File

@@ -71,6 +71,34 @@ vich_uploader:
inject_on_load: false
delete_on_update: true
delete_on_remove: true
order_cgv:
uri_prefix: /storage/order_cgv
upload_destination: '%kernel.project_dir%/public/storage/order_cgv'
namer: Vich\UploaderBundle\Naming\SmartUniqueNamer # Replaced namer
inject_on_load: false
delete_on_update: true
delete_on_remove: true
order_cgv_audit:
uri_prefix: /storage/order_cgv_audit
upload_destination: '%kernel.project_dir%/public/storage/order_cgv_audit'
namer: Vich\UploaderBundle\Naming\SmartUniqueNamer # Replaced namer
inject_on_load: false
delete_on_update: true
delete_on_remove: true
order_contrat:
uri_prefix: /storage/order_contrat
upload_destination: '%kernel.project_dir%/public/storage/order_contrat'
namer: Vich\UploaderBundle\Naming\SmartUniqueNamer # Replaced namer
inject_on_load: false
delete_on_update: true
delete_on_remove: true
order_contrat_audit:
uri_prefix: /storage/order_contrat_audit
upload_destination: '%kernel.project_dir%/public/storage/order_contrat_audit'
namer: Vich\UploaderBundle\Naming\SmartUniqueNamer # Replaced namer
inject_on_load: false
delete_on_update: true
delete_on_remove: true
#mappings:
# products:
# uri_prefix: /images/products

View File

@@ -0,0 +1,37 @@
<?php
declare(strict_types=1);
namespace DoctrineMigrations;
use Doctrine\DBAL\Schema\Schema;
use Doctrine\Migrations\AbstractMigration;
/**
* Auto-generated Migration: Please modify to your needs!
*/
final class Version20251104190740 extends AbstractMigration
{
public function getDescription(): string
{
return '';
}
public function up(Schema $schema): void
{
// this up() migration is auto-generated, please modify it to your needs
$this->addSql('CREATE TABLE "order" (id SERIAL NOT NULL, raison_social VARCHAR(255) DEFAULT NULL, name VARCHAR(255) DEFAULT NULL, surname VARCHAR(255) DEFAULT NULL, email VARCHAR(255) DEFAULT NULL, phone VARCHAR(255) DEFAULT NULL, uuid UUID NOT NULL, state VARCHAR(255) NOT NULL, payment_id VARCHAR(255) DEFAULT NULL, submision_id VARCHAR(255) DEFAULT NULL, siret VARCHAR(255) DEFAULT NULL, type VARCHAR(255) DEFAULT NULL, namewebsite VARCHAR(255) DEFAULT NULL, create_at TIMESTAMP(0) WITHOUT TIME ZONE NOT NULL, update_at TIMESTAMP(0) WITHOUT TIME ZONE NOT NULL, cgv_file_name VARCHAR(255) DEFAULT NULL, cgv_dimensions JSON DEFAULT NULL, cgv_size VARCHAR(255) DEFAULT NULL, cgv_mine_type VARCHAR(255) DEFAULT NULL, cgv_original_name VARCHAR(255) DEFAULT NULL, cgv_audit_file_name VARCHAR(255) DEFAULT NULL, cgv_audit_dimensions JSON DEFAULT NULL, cgv_audit_size VARCHAR(255) DEFAULT NULL, cgv_audit_mine_type VARCHAR(255) DEFAULT NULL, cgv_audit_original_name VARCHAR(255) DEFAULT NULL, order_contrat_file_name VARCHAR(255) DEFAULT NULL, order_contrat_dimensions JSON DEFAULT NULL, order_contrat_size VARCHAR(255) DEFAULT NULL, order_contrat_mine_type VARCHAR(255) DEFAULT NULL, order_contrat_original_name VARCHAR(255) DEFAULT NULL, order_contrat_audit_file_name VARCHAR(255) DEFAULT NULL, order_contrat_audit_dimensions JSON DEFAULT NULL, order_contrat_audit_size VARCHAR(255) DEFAULT NULL, order_contrat_audit_mine_type VARCHAR(255) DEFAULT NULL, order_contrat_audit_original_name VARCHAR(255) DEFAULT NULL, PRIMARY KEY(id))');
$this->addSql('COMMENT ON COLUMN "order".uuid IS \'(DC2Type:uuid)\'');
$this->addSql('COMMENT ON COLUMN "order".create_at IS \'(DC2Type:datetime_immutable)\'');
$this->addSql('COMMENT ON COLUMN "order".update_at IS \'(DC2Type:datetime_immutable)\'');
$this->addSql('CREATE TABLE order_website (id SERIAL NOT NULL, id_formule INT NOT NULL, PRIMARY KEY(id))');
}
public function down(Schema $schema): void
{
// this down() migration is auto-generated, please modify it to your needs
$this->addSql('CREATE SCHEMA public');
$this->addSql('DROP TABLE "order"');
$this->addSql('DROP TABLE order_website');
}
}

View File

@@ -0,0 +1,36 @@
<?php
declare(strict_types=1);
namespace DoctrineMigrations;
use Doctrine\DBAL\Schema\Schema;
use Doctrine\Migrations\AbstractMigration;
/**
* Auto-generated Migration: Please modify to your needs!
*/
final class Version20251104191430 extends AbstractMigration
{
public function getDescription(): string
{
return '';
}
public function up(Schema $schema): void
{
// this up() migration is auto-generated, please modify it to your needs
$this->addSql('ALTER TABLE "order" ADD id_formule INT NOT NULL');
$this->addSql('ALTER TABLE "order" ADD is_ndd BOOLEAN NOT NULL');
$this->addSql('ALTER TABLE "order" ADD ndd VARCHAR(255) DEFAULT NULL');
}
public function down(Schema $schema): void
{
// this down() migration is auto-generated, please modify it to your needs
$this->addSql('CREATE SCHEMA public');
$this->addSql('ALTER TABLE "order" DROP id_formule');
$this->addSql('ALTER TABLE "order" DROP is_ndd');
$this->addSql('ALTER TABLE "order" DROP ndd');
}
}

View File

@@ -4,7 +4,11 @@ declare(strict_types=1);
namespace App\Controller\Order;
use App\Entity\Order;
use App\Form\Artemis\Order\OrderType;
use Doctrine\ORM\EntityManagerInterface;
use Iodev\Whois\Factory;
use Ramsey\Uuid\Uuid;
use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
use Symfony\Component\HttpFoundation\JsonResponse;
use Symfony\Component\HttpFoundation\Request;
@@ -722,14 +726,48 @@ class HomeController extends AbstractController
],
];
#[Route('/commande/process', name: 'commande_process')]
public function process(Request $request): Response
#[Route('/commande/process/{id}', name: 'commande_process_flow')]
public function processView(?Order $order,Request $request): Response
{
if(!$order instanceof Order){
return $this->redirectToRoute('commande');
}
$form = $this->createForm(OrderType::class,$order);
$form->handleRequest($request);
return $this->render('order/flow.twig', [
'form' => $form->createView(),
'formules' => self::formules,
]);
}
#[Route('/commande/process', name: 'commande_process')]
public function process(Request $request,EntityManagerInterface $entityManager): Response
{
if($request->isMethod('POST')) {
$data = $request->request->all();
$order = new Order();
$order->setIdFormule(intval($request->request->get('formule')));
$order->setIsNdd($data['options']['domaine']['activate'] == "1");
if($data['options']['domaine']['activate'] == "1") {
$order->setNdd($data['options']['domaine']['name']);
}
$order->setUuid(\Symfony\Component\Uid\Uuid::v4());
$order->setState("created");
$order->setCreateAt(new \DateTimeImmutable());
$order->setUpdateAt(new \DateTimeImmutable());
$entityManager->persist($order);
$entityManager->flush();
return $this->redirectToRoute('commande_process_flow',['id'=>$order->getId()]);
}
if(!$request->query->has('formule'))
return $this->redirectToRoute('commande');
$formule = $request->query->get('formule');
if(!isset(self::formulesList[$formule]))
return $this->redirectToRoute('commande');
return $this->render('order/process.twig', [
'formules' => self::formules,
'currentFormule' => self::formulesList[$formule],

698
src/Entity/Order.php Normal file
View File

@@ -0,0 +1,698 @@
<?php
namespace App\Entity;
use App\Repository\OrderRepository;
use Doctrine\ORM\Mapping as ORM;
use Symfony\Component\HttpFoundation\File\File;
use Symfony\Component\Uid\Uuid;
use Vich\UploaderBundle\Mapping\Annotation as Vich;
#[ORM\Entity(repositoryClass: OrderRepository::class)]
#[ORM\Table(name: '`order`')]
#[Vich\Uploadable()]
class Order
{
#[ORM\Id]
#[ORM\GeneratedValue]
#[ORM\Column]
private ?int $id = null;
#[ORM\Column(length: 255, nullable: true)]
private ?string $raisonSocial = null;
#[ORM\Column(length: 255,nullable: true)]
private ?string $name = null;
#[ORM\Column(length: 255,nullable: true)]
private ?string $surname = null;
#[ORM\Column(length: 255,nullable: true)]
private ?string $email = null;
#[ORM\Column(length: 255,nullable: true)]
private ?string $phone = null;
#[ORM\Column(type: 'uuid')]
private ?Uuid $uuid = null;
#[ORM\Column(length: 255)]
private ?string $state = null;
#[ORM\Column(length: 255,nullable: true)]
private ?string $paymentId = null;
#[ORM\Column(length: 255,nullable: true)]
private ?string $submisionId = null;
#[ORM\Column(length: 255, nullable: true)]
private ?string $siret = null;
#[ORM\Column(length: 255,nullable: true)]
private ?string $type = null;
#[ORM\Column(length: 255,nullable: true)]
private ?string $namewebsite = null;
#[ORM\Column]
private ?\DateTimeImmutable $createAt = null;
#[ORM\Column]
private ?\DateTimeImmutable $updateAt = null;
#[Vich\UploadableField(mapping: 'order_cgv',fileNameProperty: 'cgvFileName', size: 'cgvSize', mimeType: 'cgvMineType', originalName: 'cgvOriginalName',dimensions: 'cgvDimensions')]
private ?File $cgv = null;
#[ORM\Column(nullable: true)]
private ?string $cgvFileName = null;
#[ORM\Column(nullable: true)]
private ?array $cgvDimensions = [];
#[ORM\Column(length: 255,nullable: true)]
private ?string $cgvSize = null;
#[ORM\Column(length: 255,nullable: true)]
private ?string $cgvMineType = null;
#[ORM\Column(length: 255,nullable: true)]
private ?string $cgvOriginalName = null;
#[Vich\UploadableField(mapping: 'order_cgv_audit',fileNameProperty: 'cgvAuditFileName', size: 'cgvAuditSize', mimeType: 'cgvAuditMineType', originalName: 'cgvAuditOriginalName',dimensions: 'cgvAuditDimensions')]
private ?File $cgvAudit = null;
#[ORM\Column(nullable: true)]
private ?string $cgvAuditFileName = null;
#[ORM\Column(nullable: true)]
private ?array $cgvAuditDimensions = [];
#[ORM\Column(length: 255,nullable: true)]
private ?string $cgvAuditSize = null;
#[ORM\Column(length: 255,nullable: true)]
private ?string $cgvAuditMineType = null;
#[ORM\Column(length: 255,nullable: true)]
private ?string $cgvAuditOriginalName = null;
#[Vich\UploadableField(mapping: 'order_contrat',fileNameProperty: 'orderContratAuditFileName', size: 'orderContratAuditSize', mimeType: 'orderContratAuditMineType', originalName: 'orderContratAuditOriginalName',dimensions: 'orderContratAuditDimensions')]
private ?File $orderContrat= null;
#[ORM\Column(nullable: true)]
private ?string $orderContratFileName = null;
#[ORM\Column(nullable: true)]
private ?array $orderContratDimensions = [];
#[ORM\Column(length: 255,nullable: true)]
private ?string $orderContratSize = null;
#[ORM\Column(length: 255,nullable: true)]
private ?string $orderContratMineType = null;
#[ORM\Column(length: 255,nullable: true)]
private ?string $orderContratOriginalName = null;
#[Vich\UploadableField(mapping: 'order_contrat_audit',fileNameProperty: 'orderContratAuditFileName', size: 'orderContratAuditSize', mimeType: 'orderContratAuditMineType', originalName: 'orderContratAuditOriginalName',dimensions: 'orderContratAuditDimensions')]
private ?File $orderContratAudit = null;
#[ORM\Column(nullable: true)]
private ?string $orderContratAuditFileName = null;
#[ORM\Column(nullable: true)]
private ?array $orderContratAuditDimensions = [];
#[ORM\Column(length: 255,nullable: true)]
private ?string $orderContratAuditSize = null;
#[ORM\Column(length: 255,nullable: true)]
private ?string $orderContratAuditMineType = null;
#[ORM\Column(length: 255,nullable: true)]
private ?string $orderContratAuditOriginalName = null;
#[ORM\Column]
private ?int $idFormule = null;
#[ORM\Column]
private ?bool $isNdd = null;
#[ORM\Column(length: 255,nullable: true)]
private ?string $ndd = null;
public function getId(): ?int
{
return $this->id;
}
public function getRaisonSocial(): ?string
{
return $this->raisonSocial;
}
public function setRaisonSocial(?string $raisonSocial): static
{
$this->raisonSocial = $raisonSocial;
return $this;
}
public function getName(): ?string
{
return $this->name;
}
public function setName(string $name): static
{
$this->name = $name;
return $this;
}
public function getSurname(): ?string
{
return $this->surname;
}
public function setSurname(string $surname): static
{
$this->surname = $surname;
return $this;
}
public function getEmail(): ?string
{
return $this->email;
}
public function setEmail(string $email): static
{
$this->email = $email;
return $this;
}
public function getPhone(): ?string
{
return $this->phone;
}
public function setPhone(string $phone): static
{
$this->phone = $phone;
return $this;
}
public function getUuid(): ?Uuid
{
return $this->uuid;
}
public function setUuid(Uuid $uuid): static
{
$this->uuid = $uuid;
return $this;
}
public function getState(): ?string
{
return $this->state;
}
public function setState(string $state): static
{
$this->state = $state;
return $this;
}
public function getPaymentId(): ?string
{
return $this->paymentId;
}
public function setPaymentId(string $paymentId): static
{
$this->paymentId = $paymentId;
return $this;
}
public function getSubmisionId(): ?string
{
return $this->submisionId;
}
public function setSubmisionId(string $submisionId): static
{
$this->submisionId = $submisionId;
return $this;
}
public function getSiret(): ?string
{
return $this->siret;
}
public function setSiret(?string $siret): static
{
$this->siret = $siret;
return $this;
}
public function getType(): ?string
{
return $this->type;
}
public function setType(string $type): static
{
$this->type = $type;
return $this;
}
public function getNamewebsite(): ?string
{
return $this->namewebsite;
}
public function setNamewebsite(string $namewebsite): static
{
$this->namewebsite = $namewebsite;
return $this;
}
public function getCreateAt(): ?\DateTimeImmutable
{
return $this->createAt;
}
public function setCreateAt(\DateTimeImmutable $createAt): static
{
$this->createAt = $createAt;
return $this;
}
/**
* @param File|null $cgv
*/
public function setCgv(?File $cgv): static
{
$this->cgv = $cgv;
if($this->cgv != null) {
$this->updateAt = new \DateTimeImmutable();
}
return $this;
}
public function getCgv(): ?File
{
return $this->cgv;
}
public function setCgvAudit(?File $cgvAudit): static
{
$this->cgvAudit = $cgvAudit;
if($this->cgvAudit != null) {
$this->updateAt = new \DateTimeImmutable();
}
return $this;
}
public function getCgvAudit(): ?File
{
return $this->cgvAudit;
}
public function getCgvSize(): ?string
{
return $this->cgvSize;
}
public function setCgvSize(?string $cgvSize): static
{
$this->cgvSize = $cgvSize;
return $this;
}
public function setCgvAuditSize(?string $cgvAuditSize): static
{
$this->cgvAuditSize = $cgvAuditSize;
return $this;
}
public function getCgvAuditDimensions(): ?array
{
return $this->cgvAuditDimensions;
}
public function setCgvAuditDimensions(?array $cgvAuditDimensions): static
{
$this->cgvAuditDimensions = $cgvAuditDimensions;
return $this;
}
public function getCgvDimensions(): ?array
{
return $this->cgvDimensions;
}
public function setCgvDimensions(?array $cgvDimensions): static
{
$this->cgvDimensions = $cgvDimensions;
return $this;
}
public function getCgvOriginalName(): ?string
{
return $this->cgvOriginalName;
}
public function setCgvAuditOriginalName(?string $cgvAuditOriginalName): static
{
$this->cgvAuditOriginalName = $cgvAuditOriginalName;
return $this;
}
public function getCgvAuditOriginalName(): ?string
{
return $this->cgvAuditOriginalName;
}
public function setCgvOriginalName(?string $cgvOriginalName): static
{
$this->cgvOriginalName = $cgvOriginalName;
return $this;
}
/**
* @return string|null
*/
public function getCgvAuditFileName(): ?string
{
return $this->cgvAuditFileName;
}
/**
* @return string|null
*/
public function getCgvAuditMineType(): ?string
{
return $this->cgvAuditMineType;
}
/**
* @return \DateTimeImmutable|null
*/
public function getUpdateAt(): ?\DateTimeImmutable
{
return $this->updateAt;
}
/**
* @return string|null
*/
public function getCgvAuditSize(): ?string
{
return $this->cgvAuditSize;
}
/**
* @return string|null
*/
public function getCgvFileName(): ?string
{
return $this->cgvFileName;
}
/**
* @return string|null
*/
public function getCgvMineType(): ?string
{
return $this->cgvMineType;
}
/**
* @param \DateTimeImmutable|null $updateAt
*/
public function setUpdateAt(?\DateTimeImmutable $updateAt): void
{
$this->updateAt = $updateAt;
}
/**
* @param string|null $cgvAuditFileName
*/
public function setCgvAuditFileName(?string $cgvAuditFileName): void
{
$this->cgvAuditFileName = $cgvAuditFileName;
}
/**
* @param string|null $cgvAuditMineType
*/
public function setCgvAuditMineType(?string $cgvAuditMineType): void
{
$this->cgvAuditMineType = $cgvAuditMineType;
}
/**
* @param string|null $cgvFileName
*/
public function setCgvFileName(?string $cgvFileName): void
{
$this->cgvFileName = $cgvFileName;
}
/**
* @param string|null $cgvMineType
*/
public function setCgvMineType(?string $cgvMineType): void
{
$this->cgvMineType = $cgvMineType;
}
/**
* @return File|null
*/
public function getOrderContrat(): ?File
{
return $this->orderContrat;
}
/**
* @return File|null
*/
public function getOrderContratAudit(): ?File
{
return $this->orderContratAudit;
}
/**
* @return array|null
*/
public function getOrderContratAuditDimensions(): ?array
{
return $this->orderContratAuditDimensions;
}
/**
* @return string|null
*/
public function getOrderContratAuditFileName(): ?string
{
return $this->orderContratAuditFileName;
}
/**
* @return string|null
*/
public function getOrderContratAuditMineType(): ?string
{
return $this->orderContratAuditMineType;
}
/**
* @return string|null
*/
public function getOrderContratAuditOriginalName(): ?string
{
return $this->orderContratAuditOriginalName;
}
/**
* @return string|null
*/
public function getOrderContratAuditSize(): ?string
{
return $this->orderContratAuditSize;
}
/**
* @return array|null
*/
public function getOrderContratDimensions(): ?array
{
return $this->orderContratDimensions;
}
/**
* @return string|null
*/
public function getOrderContratFileName(): ?string
{
return $this->orderContratFileName;
}
/**
* @return string|null
*/
public function getOrderContratMineType(): ?string
{
return $this->orderContratMineType;
}
/**
* @return string|null
*/
public function getOrderContratOriginalName(): ?string
{
return $this->orderContratOriginalName;
}
/**
* @return string|null
*/
public function getOrderContratSize(): ?string
{
return $this->orderContratSize;
}
/**
* @param File|null $orderContrat
*/
public function setOrderContrat(?File $orderContrat): void
{
$this->orderContrat = $orderContrat;
}
/**
* @param File|null $orderContratAudit
*/
public function setOrderContratAudit(?File $orderContratAudit): void
{
$this->orderContratAudit = $orderContratAudit;
}
/**
* @param array|null $orderContratAuditDimensions
*/
public function setOrderContratAuditDimensions(?array $orderContratAuditDimensions): void
{
$this->orderContratAuditDimensions = $orderContratAuditDimensions;
}
/**
* @param string|null $orderContratAuditFileName
*/
public function setOrderContratAuditFileName(?string $orderContratAuditFileName): void
{
$this->orderContratAuditFileName = $orderContratAuditFileName;
}
/**
* @param string|null $orderContratAuditMineType
*/
public function setOrderContratAuditMineType(?string $orderContratAuditMineType): void
{
$this->orderContratAuditMineType = $orderContratAuditMineType;
}
/**
* @param string|null $orderContratAuditOriginalName
*/
public function setOrderContratAuditOriginalName(?string $orderContratAuditOriginalName): void
{
$this->orderContratAuditOriginalName = $orderContratAuditOriginalName;
}
/**
* @param string|null $orderContratAuditSize
*/
public function setOrderContratAuditSize(?string $orderContratAuditSize): void
{
$this->orderContratAuditSize = $orderContratAuditSize;
}
/**
* @param array|null $orderContratDimensions
*/
public function setOrderContratDimensions(?array $orderContratDimensions): void
{
$this->orderContratDimensions = $orderContratDimensions;
}
/**
* @param string|null $orderContratFileName
*/
public function setOrderContratFileName(?string $orderContratFileName): void
{
$this->orderContratFileName = $orderContratFileName;
}
/**
* @param string|null $orderContratMineType
*/
public function setOrderContratMineType(?string $orderContratMineType): void
{
$this->orderContratMineType = $orderContratMineType;
}
/**
* @param string|null $orderContratOriginalName
*/
public function setOrderContratOriginalName(?string $orderContratOriginalName): void
{
$this->orderContratOriginalName = $orderContratOriginalName;
}
/**
* @param string|null $orderContratSize
*/
public function setOrderContratSize(?string $orderContratSize): void
{
$this->orderContratSize = $orderContratSize;
}
public function getIdFormule(): ?int
{
return $this->idFormule;
}
public function setIdFormule(int $idFormule): static
{
$this->idFormule = $idFormule;
return $this;
}
public function isNdd(): ?bool
{
return $this->isNdd;
}
public function setIsNdd(bool $isNdd): static
{
$this->isNdd = $isNdd;
return $this;
}
public function getNdd(): ?string
{
return $this->ndd;
}
public function setNdd(string $ndd): static
{
$this->ndd = $ndd;
return $this;
}
}

View File

@@ -0,0 +1,35 @@
<?php
namespace App\Entity;
use App\Repository\OrderWebsiteRepository;
use Doctrine\ORM\Mapping as ORM;
#[ORM\Entity(repositoryClass: OrderWebsiteRepository::class)]
class OrderWebsite
{
#[ORM\Id]
#[ORM\GeneratedValue]
#[ORM\Column]
private ?int $id = null;
#[ORM\Column]
private ?int $idFormule = null;
public function getId(): ?int
{
return $this->id;
}
public function getIdFormule(): ?int
{
return $this->idFormule;
}
public function setIdFormule(int $idFormule): static
{
$this->idFormule = $idFormule;
return $this;
}
}

View File

@@ -0,0 +1,64 @@
<?php
namespace App\Form\Artemis\Order;
use App\Entity\Order;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\Extension\Core\Type\ChoiceType;
use Symfony\Component\Form\Extension\Core\Type\EmailType;
use Symfony\Component\Form\Extension\Core\Type\TelType;
use Symfony\Component\Form\Extension\Core\Type\TextType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolver;
class OrderType extends AbstractType
{
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder
->add('namewebsite',TextType::class,[
'label' => 'Nom du site',
'required' => true,
])
->add('name',TextType::class,[
'label' => 'Nom',
'required' => true,
])
->add('surname',TextType::class,[
'label' => 'Prénom',
'required' => true,
])
->add('raisonSocial',TextType::class,[
'label' => 'Raison social',
'required' => true,
])
->add('phone',TelType::class,[
'label' => 'Téléphone',
'required' => true,
])
->add('email',EmailType::class,[
'label' => 'Email',
'required' => true,
])
->add('siret',TextType::class,[
'label' => 'Siren',
'required' => false,
'help' => 'Si vous avez un numéro'
])
->add('type',ChoiceType::class,[
'label' => 'Type',
'choices' => [
'Particulier' => 'particulier',
'Entreprise Individuelle' => 'ie',
'Association' => 'association',
'Mairie' => 'mairie',
'PME' => 'pme'
]
]);
}
public function configureOptions(OptionsResolver $resolver)
{
$resolver->setDefault('data_class',Order::class);
}
}

View File

@@ -0,0 +1,43 @@
<?php
namespace App\Repository;
use App\Entity\Order;
use Doctrine\Bundle\DoctrineBundle\Repository\ServiceEntityRepository;
use Doctrine\Persistence\ManagerRegistry;
/**
* @extends ServiceEntityRepository<Order>
*/
class OrderRepository extends ServiceEntityRepository
{
public function __construct(ManagerRegistry $registry)
{
parent::__construct($registry, Order::class);
}
// /**
// * @return Order[] Returns an array of Order objects
// */
// public function findByExampleField($value): array
// {
// return $this->createQueryBuilder('o')
// ->andWhere('o.exampleField = :val')
// ->setParameter('val', $value)
// ->orderBy('o.id', 'ASC')
// ->setMaxResults(10)
// ->getQuery()
// ->getResult()
// ;
// }
// public function findOneBySomeField($value): ?Order
// {
// return $this->createQueryBuilder('o')
// ->andWhere('o.exampleField = :val')
// ->setParameter('val', $value)
// ->getQuery()
// ->getOneOrNullResult()
// ;
// }
}

View File

@@ -0,0 +1,43 @@
<?php
namespace App\Repository;
use App\Entity\OrderWebsite;
use Doctrine\Bundle\DoctrineBundle\Repository\ServiceEntityRepository;
use Doctrine\Persistence\ManagerRegistry;
/**
* @extends ServiceEntityRepository<OrderWebsite>
*/
class OrderWebsiteRepository extends ServiceEntityRepository
{
public function __construct(ManagerRegistry $registry)
{
parent::__construct($registry, OrderWebsite::class);
}
// /**
// * @return OrderWebsite[] Returns an array of OrderWebsite objects
// */
// public function findByExampleField($value): array
// {
// return $this->createQueryBuilder('o')
// ->andWhere('o.exampleField = :val')
// ->setParameter('val', $value)
// ->orderBy('o.id', 'ASC')
// ->setMaxResults(10)
// ->getQuery()
// ->getResult()
// ;
// }
// public function findOneBySomeField($value): ?OrderWebsite
// {
// return $this->createQueryBuilder('o')
// ->andWhere('o.exampleField = :val')
// ->setParameter('val', $value)
// ->getQuery()
// ->getOneOrNullResult()
// ;
// }
}

79
templates/order/flow.twig Normal file
View File

@@ -0,0 +1,79 @@
{% extends 'order/base.twig' %}
{% block content %}
<div class="flex justify-center py-12 px-4 sm:px-6 lg:px-8 bg-gray-50">
<div class="max-w-4xl w-full space-y-8 bg-white p-8 md:p-10 shadow-xl rounded-lg border border-gray-200">
<h2 class="text-3xl font-extrabold text-gray-900 text-center">
Détails de la Commande et Contact
</h2>
{{ form_start(form, {'attr': {'class': 'mt-8 space-y-6'}}) }}
<div class="grid grid-cols-1 md:grid-cols-2 gap-6">
{#
Conteneur principal: grille à 1 colonne sur mobile (sm:) et 2 colonnes sur desktop (md:)
Chaque 'div' représente le conteneur d'un champ (form_row).
#}
<div>
<label class="block text-sm font-medium text-gray-700">{{ form.namewebsite.vars.label|default('Nom du site internet') }}</label>
{{ form_widget(form.namewebsite, {'attr': {'class': 'mt-1 block w-full border border-gray-300 rounded-md shadow-sm py-2 px-3 focus:outline-none focus:ring-indigo-500 focus:border-indigo-500 sm:text-sm', 'placeholder': 'Nom du site internet'}}) }}
{{ form_errors(form.namewebsite) }}
</div>
{# Ligne 1: Nom et Prénom sur deux colonnes #}
<div>
<label class="block text-sm font-medium text-gray-700">{{ form.name.vars.label|default('Nom') }}</label>
{{ form_widget(form.name, {'attr': {'class': 'mt-1 block w-full border border-gray-300 rounded-md shadow-sm py-2 px-3 focus:outline-none focus:ring-indigo-500 focus:border-indigo-500 sm:text-sm', 'placeholder': 'Votre nom de famille'}}) }}
{{ form_errors(form.name) }}
</div>
<div>
<label class="block text-sm font-medium text-gray-700">{{ form.surname.vars.label|default('Prénom') }}</label>
{{ form_widget(form.surname, {'attr': {'class': 'mt-1 block w-full border border-gray-300 rounded-md shadow-sm py-2 px-3 focus:outline-none focus:ring-indigo-500 focus:border-indigo-500 sm:text-sm', 'placeholder': 'Votre prénom'}}) }}
{{ form_errors(form.surname) }}
</div>
{# Ligne 2: Téléphone et Email sur deux colonnes #}
<div>
<label class="block text-sm font-medium text-gray-700">{{ form.phone.vars.label|default('Téléphone') }}</label>
{{ form_widget(form.phone, {'attr': {'class': 'mt-1 block w-full border border-gray-300 rounded-md shadow-sm py-2 px-3 focus:outline-none focus:ring-indigo-500 focus:border-indigo-500 sm:text-sm', 'placeholder': '06 00 00 00 00'}}) }}
{{ form_errors(form.phone) }}
</div>
<div>
<label class="block text-sm font-medium text-gray-700">{{ form.email.vars.label|default('Email') }}</label>
{{ form_widget(form.email, {'attr': {'class': 'mt-1 block w-full border border-gray-300 rounded-md shadow-sm py-2 px-3 focus:outline-none focus:ring-indigo-500 focus:border-indigo-500 sm:text-sm', 'placeholder': 'exemple@email.com'}}) }}
{{ form_errors(form.email) }}
</div>
{# Ligne 3: Raison Sociale et SIRET sur deux colonnes #}
<div>
<label class="block text-sm font-medium text-gray-700">{{ form.raisonSocial.vars.label|default('Raison Sociale') }}</label>
{{ form_widget(form.raisonSocial, {'attr': {'class': 'mt-1 block w-full border border-gray-300 rounded-md shadow-sm py-2 px-3 focus:outline-none focus:ring-indigo-500 focus:border-indigo-500 sm:text-sm', 'placeholder': 'Nom de l\'entreprise'}}) }}
{{ form_errors(form.raisonSocial) }}
</div>
<div>
<label class="block text-sm font-medium text-gray-700">{{ form.siret.vars.label|default('Numéro SIRET') }}</label>
{{ form_widget(form.siret, {'attr': {'class': 'mt-1 block w-full border border-gray-300 rounded-md shadow-sm py-2 px-3 focus:outline-none focus:ring-indigo-500 focus:border-indigo-500 sm:text-sm', 'placeholder': '14 chiffres sans espaces'}}) }}
{{ form_errors(form.siret) }}
</div>
</div>
{# Champ Type (souvent un Select/Choix, pleine largeur) #}
<div class="pt-4">
<label class="block text-sm font-medium text-gray-700">{{ form.type.vars.label|default('Type de commande') }}</label>
{{ form_widget(form.type, {'attr': {'class': 'mt-1 block w-full border border-gray-300 bg-white rounded-md shadow-sm py-2 px-3 focus:outline-none focus:ring-indigo-500 focus:border-indigo-500 sm:text-sm'}}) }}
{{ form_errors(form.type) }}
</div>
{# Bouton de soumission #}
<div class="pt-6">
<button type="submit" class="w-full flex justify-center py-2 px-4 border border-transparent rounded-md shadow-sm text-sm font-medium text-white bg-indigo-600 hover:bg-indigo-700 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-indigo-500">
Soumettre la Commande
</button>
</div>
{{ form_end(form) }}
</div>
</div>
{% endblock %}

View File

@@ -24,7 +24,7 @@
{# Vérification pour s'assurer qu'une formule est bien présente #}
{% if currentFormule is defined and currentFormule is not empty %}
<form action="{{ path('commande_process') }}" method="POST" id="order-form">
<form action="{{ path('commande_process') }}?formule={{ currentFormule.id }}" method="POST" id="order-form">
{# Conteneur principal en grille : 3/4 pour le formulaire, 1/4 pour le récapitulatif #}
<div class="lg:grid lg:grid-cols-12 lg:gap-8">
@@ -358,7 +358,9 @@
// Mise à jour de l'affichage
initialTotalEl.textContent = formatPrice(currentInitialTotal); // MISE À JOUR DU TOTAL INITIAL
monthlyTotalEl.textContent = formatPrice(currentMonthlyTotal);
if(monthlyTotalEl != undefined) {
monthlyTotalEl.textContent = formatPrice(currentMonthlyTotal);
}
annualTotalEl.textContent = formatPrice(currentAnnualTotal);
selectedOptionsList.innerHTML = selectedOptionsHtml;