ldc-boutique-cnc/app/Http/Controllers/Bo/OrdersController.php
2021-04-14 09:34:23 +02:00

287 lines
9.6 KiB
PHP

<?php
namespace App\Http\Controllers\Bo;
use App\Http\Controllers\Controller;
use App\Models\Order;
use App\Models\OrderLine;
use App\Models\OrdersProducts;
use App\Models\Product;
use App\Models\Timeslot;
use Illuminate\Support\Facades\Mail;
use App\Mail\OrderConfirmMail;
use App\Models\Customers;
use Carbon\Carbon;
use Carbon\CarbonImmutable;
use Carbon\CarbonInterval;
use Gloudemans\Shoppingcart\Facades\Cart;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Str;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Session;
class OrdersController extends Controller
{
/**
* index of orders (Bo)
*/
public function index() {
$orders = Order::orderBy('date', 'DESC')->get();
return view('bo.orders.index', compact('orders'));
}
/**
* action de changement de statut vers l'avant
* @todo : envoyer les mails transactionnels
*/
public function changeStatus($reference) {
$order = Order::where('reference', $reference)->first();
$order->status_id = $order->status_id + 1;
$order->save();
//return redirect()->route('bo.orders')->with('success', "Changement de status enregistré pour la commande " . $order->reference . ".");
return back()->with('success', "Changement de status enregistré pour la commande " . $order->reference . ".");
}
/**
* mise au statut annulé d'une commande
*/
public function cancelOrder($reference) {
$order = Order::where('reference', $reference)->first();
$order->status_id = 7;
$order->save();
//return redirect()->route('bo.orders')->with('success', "La commande à été annulée.");
return back()->with('success', "La commande " . $order->reference . " à été annulée.");
}
/**
* @deprecated
* ajout de produits à la commande
* @todo : supprimer cette méthode qui repose sur un modèle de donnée osolète
*/
public function addProduct($orderReference, $productId, $quantity) {
$product = Product::findOrFail($productId);
$order = Order::where('reference', $orderReference)->first();
$order->total = $order->total + (($product->price - $product->price_buy) * $quantity);
$orderProduct = new OrdersProducts();
$orderProduct->product_id = $product->id;
$orderProduct->order_id = $order->id;
$orderProduct->quantity = $quantity;
$orderProduct->save();
return redirect()->route('bo.orders')->with('success', "Le produit à été ajouté.");
}
/**
* front
* récap panier du tunnel de commande
* @todo : déplacer vers le controller idoine
*/
public function recapOrder()
{
$activestep = 2;
$cart = Cart::content();
$cartInfos = array(
"totalTTC" => Cart::total(),
'totalTVA' => Cart::tax(), //total des taxes
'totalHT' => Cart::subtotal(), //total sans les taxes
'totalweight' => Cart::weight(), //poids total des items
'totalHTbefore' => Cart::priceTotal(), //total avant taxes et remises
'totaldiscount' => Cart::discount(), //total des remises
'countItems' => Cart::count(), //nb de produits dans le cart
);
return view('sales.recap', compact('activestep', 'cart', 'cartInfos'));
}
/**
* front
* Storing order from sales tunnel
*/
public function store()
{
//save
$order = new Order();
$order->reference = Str::uuid();
$order->date = Carbon::now();
$order->status_id = 1;
$order->total = str_replace(',', '.', str_replace(' ', '', Cart::total()));
$order->customer_id = Auth::user()->id;
$order->save();
//order_id
$cart = Cart::content();
foreach ($cart as $cartItem) {
$order_line = new OrderLine();
$order_line->order_id = $order->id;
$order_line->product_id = $cartItem->model->id;
$order_line->quantity = $cartItem->qty;
//gross unit price
$order_line->unit_price = $cartItem->model->priceHt;
//discount per unit
$order_line->unit_discount = $cartItem->model->discountAmount;
//tax rate for this line
$order_line->tax_rate = $cartItem->taxRate;
//tax amount par unit
$order_line->unit_tax = (($order_line->unit_price - $order_line->unit_discount) * ($order_line->tax_rate / 100));
//discount amount for the line
$order_line->total_discount = $order_line->unit_discount * $order_line->quantity;
//gross amount for the line
$order_line->total_ht = ($order_line->unit_price - $order_line->unit_discount) * $order_line->quantity;
//tax amount for the line
$order_line->total_tax = $order_line->unit_tax * $order_line->quantity;
//total TTC avec remises de la ligne
$order_line->total_ttc = $order_line->total_ht + $order_line->total_tax;
$order_line->save();
}
//empty cart
Cart::destroy();
//then redirect
return redirect()->route('sales.pick-slot', ['reference' => $order->reference]);
}
/**
* front tunnel de commande étape 3 : choix de créneau
*/
public function timeSlotPick($reference)
{
$activestep = 3;
//settings à stocker
//get available timeslots
//days 0 = sunday => 6 = saturday
$plage = array(
0 => array(),
1 => array(
'start' =>'09:00',
'end' => '16:50',
),
2 => array(
'start' =>'09:00',
'end' => '17:00',
),
3 => array(
'start' =>'09:00',
'end' => '17:00',
),
4 => array(
'start' =>'09:00',
'end' => '17:00',
),
5 => array(
'start' =>'09:00',
'end' => '17:00',
),
6 => array(
'start' =>'10:00',
'end' => '12:00',
),
);
$plage_interval = "0:15";
$plage_days = 14;
//génération des plages
//start today
$today = CarbonImmutable::now()->startOfDay();
$now = CarbonImmutable::now();
$availCreneaux = array();
$interval = CarbonInterval::createFromFormat('h:i',$plage_interval);
for ($i = 0; $i < $plage_days; $i++) {
/** @var Carbon */
$current = $today->add($i, 'day');
$weekDay = $current->weekday();
if (isset($plage[$weekDay]['start'])) {
$currentTime = Carbon::createFromTimeString($plage[$weekDay]['start']);
$endTime = Carbon::createFromTimeString($plage[$weekDay]['end']);
do {
$creneau = $currentTime->format('H:i');
//attention si la date est passée (today mai avant maintenant) : pas de créneau
if($current > $today || $currentTime >= $now) {
$availCreneaux[$current->format('d/m/Y')][] = $creneau;
}
$currentTime->add($interval);
} while ($currentTime <= $endTime);
}
}
$order = Order::where('reference', '=', $reference)->firstOrFail();
return view('sales.pick-slot', compact('activestep', 'availCreneaux', 'order'));
}
/**
* front
* enregistrement du créneau de collect
* et validation de la commande
*/
public function setTimeSlot(Request $request)
{
$time_slot = Carbon::createFromFormat('d/m/Y-H:i', $request->selectedcreneau);
$tsday = explode('-',$request->selectedcreneau)[0];
$tstime = explode('-',$request->selectedcreneau)[1];
$reference = $request->order_ref;
$order = Order::where('reference', '=', $reference)->firstOrFail();
if($order->status_id == 1) {
// on ne traite l'enregistrement que pour les commandes en attente venant de l'étape de récap
//save timeslot
$timeslot = Timeslot::firstOrNew(['order_id' => $order->id]);
$timeslot->order_id = $order->id;
$timeslot->day = $tsday;
$timeslot->time = $tstime;
$timeslot->save();
//save order status
$order->status_id = 3;
$order->save();
//send confirm mail
Mail::to($order->customer->email)->send(new OrderConfirmMail($order));
}
//redirect to final confirmation
return redirect()->route('sales.confirm', ['reference' => $order->reference]);
}
/**
* front
* page de confirmation de commande
*/
public function confirmOrder($reference)
{
$activestep = 4;
$idcommande = Session::get('idcommande');
$order = Order::where('reference', '=', $reference)->firstOrFail();
return view('sales.confirm', compact('activestep', 'order'));
}
/**
* bo
* ajx : affichage d'infos sur un client
* @todo : déplacer dans le controller idoine
*/
public function getCustomerInfo($id) {
$cust = Customers::findOrFail($id);
return view('bo.customer.info-popup', compact('cust'));
}
/**
* bo : page détatil commande
*/
public function orderDetail($reference) {
$order = Order::where('reference', '=', $reference)->firstOrFail();
return view('bo.orders.detail', compact('order'));
}
}