diff --git a/src/Controller/ResqAPI/JobOrderController.php b/src/Controller/ResqAPI/JobOrderController.php index 1aa4b0fc..1302bf21 100644 --- a/src/Controller/ResqAPI/JobOrderController.php +++ b/src/Controller/ResqAPI/JobOrderController.php @@ -14,6 +14,7 @@ use Catalyst\APIBundle\Controller\APIController; use Catalyst\APIBundle\Response\APIResponse; use App\Ramcar\WarrantyClass; use App\Ramcar\JOStatus; +use App\Ramcar\AdvanceOrderSlot; use App\Ramcar\AutoAssignStatus; use App\Ramcar\InvoiceCriteria; use App\Ramcar\ServiceType; @@ -43,6 +44,7 @@ use App\Entity\Promo; use App\Entity\Battery; use App\Entity\JOEvent; use App\Entity\Customer; +use App\Entity\Hub; use Catalyst\APIBundle\Access\Generator as ACLGenerator; @@ -96,7 +98,7 @@ class JobOrderController extends APIController return new APIResponse(false, $msg); $jo = new JobOrder(); - $this->setJOObject($jo, $req); + $this->setJOObject($jo, $req, $em); // customer $cust = $mobile_user->getCustomer(); @@ -160,19 +162,19 @@ class JobOrderController extends APIController $this->removeCustomerTag($jo, $jo->getCustomerVehicle(), $promo_logger, $mobile_user->getID()); - return new APIResponse(true, 'Job order creatd', $data); + return new APIResponse(true, 'Job order created', $data); } - // TODO: modify for MobileUser - // break this down into smaller functions - // do we still use this? public function newRequestJobOrder(Request $req, InvoiceGeneratorInterface $ic, GeofenceTracker $geo, MapTools $map_tools, InventoryManager $im, MQTTClient $mclient, RiderAssignmentHandlerInterface $rah, PromoLogger $promo_logger, HubSelector $hub_select, HubDistributor $hub_dist, HubFilterLogger $hub_filter_logger, - HubFilteringGeoChecker $hub_geofence, EntityManagerInterface $em) + HubFilteringGeoChecker $hub_geofence, EntityManagerInterface $em, + MobileAPIHandler $mah) { - // check required parameters and api key + $this->denyAccessUnlessGranted('mobile_jo.request', null, 'No access.'); + + // check required parameters $required_params = [ 'service_type', 'cv_id', @@ -182,168 +184,40 @@ class JobOrderController extends APIController 'warranty', 'mode_of_payment', ]; - $res = $this->checkParamsAndKey($req, $em, $required_params); - if ($res->isError()) - return $res->getReturnResponse(); - // trade in type - $trade_in = $req->request->get('trade_in'); + $msg = $this->checkRequiredParameters($req, $required_params); + if ($msg) + return new APIResponse(false, $msg); - // address - $address = $req->request->get('delivery_address', 'Set by mobile application'); + // get capi user to link to mobile user + $user_id = $this->getUser()->getID(); - // instructions - $instructions = $req->request->get('delivery_instructions', ''); + // get mobile user + $mobile_user = $mah->findMobileUser($user_id); - // longitude and latitude - $long = $req->request->get('long'); - $lat = $req->request->get('lat'); + if ($mobile_user == null) + return new APIResponse(false, 'No mobile user found.'); - // geofence - $is_covered = $geo->isCovered($long, $lat); - if (!$is_covered) - { - // TODO: put geofence error message in config file somewhere - $res->setError(true) - ->setErrorMessage('Oops! Our service is limited to some areas in Metro Manila, Laguna, and Baguio only. We will update you as soon as we are able to cover your area'); - return $res->getReturnResponse(); - } - - $hub = null; - $hub_id = $req->request->get('hub_id'); - if (strlen($hub_id) > 0) - $hub = $em->getRepository(Hub::class)->find($hub_id); - - $schedule_date = $req->request->get('date_schedule'); - $slot_id = $req->request->get('slot_id'); - $advance_order = $req->request->get('flag_advance_order'); - // check for 'false' text - if ($advance_order === false || $advance_order === 0 || $advance_order === '0' || $advance_order == 'false') - $flag_advance_order = false; - else - $flag_advance_order = true; + // validate request + $msg = $this->validateJORequest($req, $geo); + if ($msg) + return new APIResponse(false, $msg); $jo = new JobOrder(); - $jo->setSource(TransactionOrigin::MOBILE_APP) - ->setStatus(JOStatus::PENDING) - ->setDeliveryInstructions('') - ->setTier1Notes('') - ->setTier2Notes('') - ->setDeliveryAddress($address) - ->setTradeInType($trade_in) - ->setDeliveryInstructions($instructions) - // TODO: error check for valid mode of payment - ->setModeOfPayment($req->request->get('mode_of_payment')) - ->setAdvanceOrder($flag_advance_order) - ->setStatusAutoAssign(AutoAssignStatus::NOT_ASSIGNED); + $this->setJOObject($jo, $req, $em); // customer - $cust = $this->session->getCustomer(); + $cust = $mobile_user->getCustomer(); if ($cust == null) - { - $res->setError(true) - ->setErrorMessage('No customer information found'); - return $res->getReturnResponse(); - } + return new APIResponse(false, 'No customer information found'); + $jo->setCustomer($cust); - // validate service type - $stype = $req->request->get('service_type'); - if (!ServiceType::validate($stype)) - { - $res->setError(true) - ->setErrorMessage('Invalid service type'); - return $res->getReturnResponse(); - } - $jo->setServiceType($stype); - - // validate warranty - $warr = $req->request->get('warranty'); - if (!WarrantyClass::validate($warr)) - { - $res->setError(true) - ->setErrorMessage('Invalid warranty class'); - return $res->getReturnResponse(); - } - $jo->setWarrantyClass($warr); - - // set coordinates - $point = new Point($long, $lat); - $jo->setCoordinates($point); - // make invoice criteria $icrit = new InvoiceCriteria(); - $icrit->setServiceType($stype); - - // check promo - $promo_id = $req->request->get('promo_id'); - if (!empty($promo_id)) - { - $promo = $em->getRepository(Promo::class)->find($promo_id); - if ($promo == null) - { - $res->setError(true) - ->setErrorMessage('Invalid promo id'); - return $res->getReturnResponse(); - } - - // put in criteria - $icrit->addPromo($promo); - } - - // check customer vehicle - $cv = $em->getRepository(CustomerVehicle::class)->find($req->request->get('cv_id')); - if ($cv == null) - { - $res->setError(true) - ->setErrorMessage('Invalid customer vehicle id'); - return $res->getReturnResponse(); - } - $icrit->setCustomerVehicle($cv); - $jo->setCustomerVehicle($cv); - - // check if customer owns vehicle - if ($cust->getID() != $cv->getCustomer()->getID()) - { - $res->setError(true) - ->setErrorMessage('Customer does not own vehicle'); - return $res->getReturnResponse(); - } - - // check battery - $batt_id = $req->request->get('batt_id'); - if ($batt_id != null) - { - $batt = $em->getRepository(Battery::class)->find($batt_id); - if ($batt == null) - { - $res->setError(true) - ->setErrorMessage('Invalid battery id'); - return $res->getReturnResponse(); - } - } - else - $batt = null; - - /* - // put battery in criteria - $icrit->addBattery($batt); - */ - - // check trade-in - // only allow motolite, other, none - switch ($trade_in) - { - case TradeInType::MOTOLITE: - case TradeInType::OTHER: - break; - - default: - $trade_in = ''; - break; - } - - $icrit->addEntry($batt, $trade_in, 1); + $msg = $this->setInvoiceCriteria($em, $icrit, $req, $cust, $jo); + if ($msg != null) + return new APIResponse(false, $msg); // send to invoice generator $invoice = $ic->generateInvoice($icrit); @@ -351,84 +225,24 @@ class JobOrderController extends APIController // assign hub and rider // check if hub is null - if ($hub == null) + if ($jo->getHub() == null) { + // set hub criteria details $hub_criteria = new HubCriteria(); - $hub_criteria->setPoint($jo->getCoordinates()); - - if ($hub_geofence->isCovered($long, $lat)) - { - // if true, set other values for HubCriteria - // TODO: set this properly, since the other flags - // are on default values - // error_log('Area is covered by hub filtering'); - $hub_criteria->setJoType($jo->getServiceType()) - ->setPaymentMethod($jo->getModeOfPayment()) - ->setRoundRobin(true); - } - - // add battery to items - $sku = $batt->getSAPCode(); - if (!empty($sku)) - $hub_criteria->addItem($batt->getSAPCode(), 1); + $this->setHubCriteria($em, $hub_geofence, $hub_criteria, $jo, $req); // find nearest hubs $nearest_hubs = $hub_select->find($hub_criteria); if (!empty($nearest_hubs)) - { - // go through the hub list, find the nearest hub - // with an available rider - //error_log('found nearest hub ' . $nearest_hub->getID()); - foreach ($nearest_hubs as $nearest_hub) - { - $available_riders = $nearest_hub['hub']->getAvailableRiders(); - if (count($available_riders) >= 1) - { - $assigned_rider = null; - if (count($available_riders) == 1) - { - $assigned_rider = $available_riders[0]; - } - else - { - // TODO: the setting of riders into an array - // will no longer be necessary when the contents - // of randomizeRider changes - $riders = []; - foreach ($available_riders as $rider) - { - $riders[] = $rider; - } - - $assigned_rider = $this->randomizeRider($riders); - } - - $jo->setHub($nearest_hub['hub']); - $jo->setRider($assigned_rider); - $jo->setStatus(JOStatus::ASSIGNED); - $jo->setStatusAutoAssign(AutoAssignStatus::HUB_AND_RIDER_ASSIGNED); - - $assigned_rider->setAvailable(false); - - // update redis hub_jo_count for hub - $hub_dist->incrementJoCountForHub($nearest_hub['hub']); - - // break out of loop - break; - } - else - { - // log hub into hub_filter_log - $hub_filter_logger->logFilteredHub($nearest_hub['hub'], 'no_available_rider'); - // continue to go through list to find hub with an available rider - } - } - } + $this->assignRider($nearest_hubs, $jo, $hub_filter_logger, $hub_dist); } else { + $schedule_date = $req->request->get('date_schedule'); + $slot_id = $req->request->get('slot_id'); $date_schedule = null; + if ((strlen($schedule_date) > 0) && (strlen($slot_id) > 0)) { $time_schedule = $this->getTimeFromSlot($slot_id); @@ -436,11 +250,10 @@ class JobOrderController extends APIController { $s_date = $schedule_date . ' ' . $time_schedule; $date_schedule = DateTime::createFromFormat('Y-m-d H:i', $s_date); - //error_log($date_schedule->format('Y-m-d H:i')); + error_log($date_schedule->format('Y-m-d H:i')); } } - $jo->setHub($hub); $jo->setStatus(JOStatus::RIDER_ASSIGN); $jo->setStatusAutoAssign(AutoAssignStatus::HUB_ASSIGNED); @@ -448,62 +261,13 @@ class JobOrderController extends APIController $jo->setDateSchedule($date_schedule); // update redis hub_jo_count for hub - $hub_dist->incrementJoCountForHub($hub); + $hub_dist->incrementJoCountForHub($jo->getHub()); } $em->persist($jo); $em->persist($invoice); - // add event log for JO - $event = new JOEvent(); - $event->setDateHappen(new DateTime()) - ->setTypeID(JOEventType::CREATE) - ->setJobOrder($jo); - $em->persist($event); - - // check JO status - if ($jo->getStatus() == JOStatus::ASSIGNED) - { - // add event logs for hub and rider assignments - $hub_assign_event = new JOEvent(); - $hub_assign_event->setDateHappen(new DateTime()) - ->setTypeID(JOEventType::HUB_ASSIGN) - ->setJobOrder($jo); - - $em->persist($hub_assign_event); - - $rider_assign_event = new JOEvent(); - $rider_assign_event->setDateHappen(new DateTime()) - ->setTypeID(JOEventType::RIDER_ASSIGN) - ->setJobOrder($jo); - - $em->persist($rider_assign_event); - - // user mqtt event - $payload = [ - 'event' => 'outlet_assign' - ]; - $mclient->sendEvent($jo, $payload); - - $rah->assignJobOrder($jo, $jo->getRider()); - } - - if ($jo->getStatus() == JOStatus::RIDER_ASSIGN) - { - // add event logs for hub assignments - $hub_assign_event = new JOEvent(); - $hub_assign_event->setDateHappen(new DateTime()) - ->setTypeID(JOEventType::HUB_ASSIGN) - ->setJobOrder($jo); - - $em->persist($hub_assign_event); - - // user mqtt event - $payload = [ - 'event' => 'outlet_assign' - ]; - $mclient->sendEvent($jo, $payload); - } + $this->processEvents($em, $jo, $rah, $mclient); $em->flush(); @@ -533,41 +297,9 @@ class JobOrderController extends APIController 'invoice' => $invoice_data ]; - // need to check for customer tag/promo - // check service type - if ($jo->getServiceType() == ServiceType::BATTERY_REPLACEMENT_NEW) - { - $customer = $cv->getCustomer(); - $customer_tags = $customer->getCustomerTagObjects(); - if (!empty($customer_tags)) - { - foreach ($customer_tags as $customer_tag) - { - if ($customer_tag->getID() == $invoice->getUsedCustomerTagId()) - { - // remove associated entity - $customer->removeCustomerTag($customer_tag); + $this->removeCustomerTag($jo, $jo->getCustomerVehicle(), $promo_logger, $mobile_user->getID()); - // log the availment of promo from customer - $created_by = $req->query->get('api_key');; - $cust_id = $jo->getCustomer()->getID(); - $cust_fname = $jo->getCustomer()->getFirstName(); - $cust_lname = $jo->getCustomer()->getLastName(); - $jo_id = $jo->getID(); - $invoice_id = $jo->getInvoice()->getID(); - // TODO: check if we store total price of invoice or just the discounted amount - $amount = $jo->getInvoice()->getTotalPrice(); - $promo_logger->logPromoInfo($created_by, $cust_id, $cust_fname, $cust_lname, $jo_id, - $invoice_id, $amount); - } - } - } - } - - // set data - $res->setData($data); - - return $res->getReturnResponse(); + return new APIResponse(true, 'Job order created', $data); } // TODO: modify for MobileUser @@ -1447,7 +1179,7 @@ class JobOrderController extends APIController return null; } - protected function setJOObject(JobOrder $jo, Request $req) + protected function setJOObject(JobOrder $jo, Request $req, EntityManagerInterface $em) { // longitude and latitude $long = $req->request->get('long'); @@ -1455,6 +1187,23 @@ class JobOrderController extends APIController $point = new Point($long, $lat); + // check for hub + $hub = null; + $hub_id = $req->request->get('hub_id'); + if (strlen($hub_id) > 0) + { + $hub = $em->getRepository(Hub::class)->find($hub_id); + $jo->setHub($hub); + } + + // check if advance order + $advance_order = $req->request->get('flag_advance_order'); + // check for 'false' text + if ($advance_order === false || $advance_order === 0 || $advance_order === '0' || $advance_order == 'false') + $flag_advance_order = false; + else + $flag_advance_order = true; + $jo->setSource(TransactionOrigin::MOBILE_APP) ->setStatus(JOStatus::PENDING) ->setDeliveryInstructions('') @@ -1466,7 +1215,9 @@ class JobOrderController extends APIController ->setModeOfPayment($req->request->get('mode_of_payment')) ->setServiceType($req->request->get('service_type')) ->setWarrantyClass($req->request->get('warranty')) - ->setCoordinates($point); + ->setCoordinates($point) + ->setAdvanceOrder($flag_advance_order) + ->setStatusAutoAssign(AutoAssignStatus::NOT_ASSIGNED); } protected function setInvoiceCriteria(EntityManagerInterface $em, InvoiceCriteria $icrit, Request $req, @@ -1665,6 +1416,22 @@ class JobOrderController extends APIController $rah->assignJobOrder($jo, $jo->getRider()); } + if ($jo->getStatus() == JOStatus::RIDER_ASSIGN) + { + // add event logs for hub assignments + $hub_assign_event = new JOEvent(); + $hub_assign_event->setDateHappen(new DateTime()) + ->setTypeID(JOEventType::HUB_ASSIGN) + ->setJobOrder($jo); + + $em->persist($hub_assign_event); + + // user mqtt event + $payload = [ + 'event' => 'outlet_assign' + ]; + $mclient->sendEvent($jo, $payload); + } } protected function removeCustomerTag(JobOrder $jo, CustomerVehicle $cv, PromoLogger $promo_logger, $mobile_user_id)