From 9ca271b51b4978a7519722dbc6bb361bd078f4af Mon Sep 17 00:00:00 2001 From: Renon Stewart Date: Fri, 24 Aug 2018 13:41:57 -0400 Subject: [PATCH] Code refactor and update admin custom price logic --- .../Order/Create/Shipping/Method/Form.php | 14 +- .../System/Config/Form/Field/Link.php | 6 +- Helper/Data.php | 88 ++++++---- Model/Carrier.php | 82 ++++++--- Plugin/Quote/Address/Total/ShippingPlugin.php | 157 +++++++++--------- composer.json | 2 +- etc/adminhtml/system.xml | 10 ++ etc/di.xml | 8 + 8 files changed, 225 insertions(+), 142 deletions(-) create mode 100644 etc/di.xml diff --git a/Block/Adminhtml/Order/Create/Shipping/Method/Form.php b/Block/Adminhtml/Order/Create/Shipping/Method/Form.php index fe1c449..b422a94 100644 --- a/Block/Adminhtml/Order/Create/Shipping/Method/Form.php +++ b/Block/Adminhtml/Order/Create/Shipping/Method/Form.php @@ -7,6 +7,8 @@ namespace MagePal\CustomShippingRate\Block\Adminhtml\Order\Create\Shipping\Method; +use MagePal\CustomShippingRate\Model\Carrier; + class Form extends \Magento\Sales\Block\Adminhtml\Order\Create\Shipping\Method\Form { protected $activeMethodRate; @@ -19,7 +21,7 @@ class Form extends \Magento\Sales\Block\Adminhtml\Order\Create\Shipping\Method\F public function getActiveCustomShippingRateMethod() { $rate = $this->getActiveMethodRate(); - return $rate && $rate->getCarrier() == \MagePal\CustomShippingRate\Model\Carrier::CODE ? $rate->getMethod() : ''; + return $rate && $rate->getCarrier() == Carrier::CODE ? $rate->getMethod() : ''; } /** @@ -44,7 +46,7 @@ public function isCustomShippingRateActive() $this->activeMethodRate = $this->getActiveMethodRate(); } - return $this->activeMethodRate && $this->activeMethodRate->getCarrier() == \MagePal\CustomShippingRate\Model\Carrier::CODE ? true : false; + return $this->activeMethodRate && $this->activeMethodRate->getCarrier() == Carrier::CODE ? true : false; } /** @@ -56,14 +58,14 @@ public function getGroupShippingRates() { $rates = $this->getShippingRates(); - if (array_key_exists(\MagePal\CustomShippingRate\Model\Carrier::CODE, $rates)) { + if (array_key_exists(Carrier::CODE, $rates)) { if (!$this->isCustomShippingRateActive()) { - unset($rates[\MagePal\CustomShippingRate\Model\Carrier::CODE]); + unset($rates[Carrier::CODE]); } else { $activeRateMethod = $this->getActiveCustomShippingRateMethod(); - foreach ($rates[\MagePal\CustomShippingRate\Model\Carrier::CODE] as $key => $rate) { + foreach ($rates[Carrier::CODE] as $key => $rate) { if ($rate->getMethod() != $activeRateMethod) { - unset($rates[\MagePal\CustomShippingRate\Model\Carrier::CODE][$key]); + unset($rates[Carrier::CODE][$key]); } } } diff --git a/Block/Adminhtml/System/Config/Form/Field/Link.php b/Block/Adminhtml/System/Config/Form/Field/Link.php index 5a2ba69..932089e 100644 --- a/Block/Adminhtml/System/Config/Form/Field/Link.php +++ b/Block/Adminhtml/System/Config/Form/Field/Link.php @@ -45,9 +45,9 @@ public function render(\Magento\Framework\Data\Form\Element\AbstractElement $ele protected function _getElementHtml(\Magento\Framework\Data\Form\Element\AbstractElement $element) { return sprintf( - '%s', - $this->_urlBuilder->getUrl('adminhtml/system_config/edit/section/carriers'), - __('Store > Configuration > Shipping Methods > Custom Shipping Rate') + '%s', + $this->_urlBuilder->getUrl('adminhtml/system_config/edit/section/carriers'), + __('Store > Configuration > Shipping Methods > Custom Shipping Rate') ); } } diff --git a/Helper/Data.php b/Helper/Data.php index 9a1d539..4a6a0bb 100644 --- a/Helper/Data.php +++ b/Helper/Data.php @@ -7,8 +7,19 @@ namespace MagePal\CustomShippingRate\Helper; +use Magento\Store\Model\ScopeInterface; +use MagePal\CustomShippingRate\Model\Carrier; + class Data extends \Magento\Framework\App\Helper\AbstractHelper { + /** + * @var array + */ + protected $shippingType; + + /** + * @var array + */ protected $codes = [ 'code' => [ 'label' => 'Code', @@ -32,6 +43,9 @@ class Data extends \Magento\Framework\App\Helper\AbstractHelper ] ]; + /** + * @var array + */ protected $headerTemplate; /** @@ -39,28 +53,50 @@ class Data extends \Magento\Framework\App\Helper\AbstractHelper */ public function getShippingType() { - $arrayValues = []; - $configData = $this->getConfigData('shipping_type'); - - if (is_string($configData) && !empty($configData) && $configData !== '[]') { - if ($this->isJson($configData)) { - $arrayValues = (array) json_decode($configData, true); - } else { - $arrayValues = (array) array_values(unserialize($configData)); + if (!$this->shippingType) { + $arrayValues = []; + $configData = $this->getConfigData('shipping_type'); + + if (is_string($configData) && !empty($configData) && $configData !== '[]') { + if ($this->isJson($configData)) { + $arrayValues = (array) json_decode($configData, true); + } else { + $arrayValues = (array) array_values(unserialize($configData)); + } } + + $arrayValues = $this->shippingArrayObject($arrayValues); + + usort($arrayValues, function ($a, $b) { + if (array_key_exists('sort_order', $a)) { + return $a['sort_order'] - $b['sort_order']; + } else { + return 0; + } + }); + + $this->shippingType = $arrayValues; } - $arrayValues = $this->shippingArrayObject($arrayValues); + return $this->shippingType; + } - usort($arrayValues, function ($a, $b) { - if (array_key_exists('sort_order', $a)) { - return $a['sort_order'] - $b['sort_order']; - } else { - return 0; + /** + * input {code}_{method} + * return method + * @param $method_code + * @return string + */ + public function getShippingCodeFromMethod($method_code) + { + foreach ($this->getShippingType() as $shippingType) { + if (Carrier::CODE . '_' . $shippingType['code'] == $method_code) { + return $shippingType['code']; + break; } - }); + } - return $arrayValues; + return ''; } /** @@ -68,27 +104,20 @@ public function getShippingType() */ public function isEnabled() { - return (bool)$this->getConfigData('active'); + return $this->scopeConfig->isSetFlag('carriers/' . Carrier::CODE . '/active'); } /** * Retrieve information from carrier configuration * * @param string $field - * @return void|false|string + * @return string */ public function getConfigData($field) { - $code = \MagePal\CustomShippingRate\Model\Carrier::CODE; - if (empty($code)) { - return false; - } - - $path = 'carriers/' . $code . '/' . $field; - return $this->scopeConfig->getValue( - $path, - \Magento\Store\Model\ScopeInterface::SCOPE_STORE + 'carriers/' . Carrier::CODE . '/' . $field, + ScopeInterface::SCOPE_STORE ); } @@ -104,6 +133,9 @@ public function isJson($string) return (json_last_error() == JSON_ERROR_NONE); } + /** + * @return array + */ public function getHeaderTemplate() { if (!$this->headerTemplate) { @@ -135,7 +167,7 @@ public function shippingArrayObject($values) $requiredFields = $this->getHeaderTemplate(); if (is_array($values)) { - foreach ($values as $key => &$row) { + foreach ($values as &$row) { $row = array_merge($requiredFields, $row); } } diff --git a/Model/Carrier.php b/Model/Carrier.php index b72a65c..bbe9b60 100644 --- a/Model/Carrier.php +++ b/Model/Carrier.php @@ -7,10 +7,20 @@ namespace MagePal\CustomShippingRate\Model; +use Magento\Backend\App\Area\FrontNameResolver; +use Magento\Framework\App\Config\ScopeConfigInterface; +use Magento\Framework\App\State; use Magento\Quote\Model\Quote\Address\RateRequest; +use Magento\Quote\Model\Quote\Address\RateResult\ErrorFactory; +use Magento\Quote\Model\Quote\Address\RateResult\MethodFactory; +use Magento\Shipping\Helper\Carrier as ShippingCarrierHelper; use Magento\Shipping\Model\Carrier\AbstractCarrier; +use Magento\Shipping\Model\Carrier\CarrierInterface; +use Magento\Shipping\Model\Rate\ResultFactory; +use MagePal\CustomShippingRate\Helper\Data; +use Psr\Log\LoggerInterface; -class Carrier extends AbstractCarrier implements \Magento\Shipping\Model\Carrier\CarrierInterface +class Carrier extends AbstractCarrier implements CarrierInterface { /** * Code of the carrier @@ -28,14 +38,14 @@ class Carrier extends AbstractCarrier implements \Magento\Shipping\Model\Carrier /** * - * @var \Magento\Quote\Model\Quote\Address\RateResult\MethodFactory + * @var MethodFactory */ protected $_rateMethodFactory; /** * Carrier helper * - * @var \Magento\Shipping\Helper\Carrier + * @var ShippingCarrierHelper */ protected $_carrierHelper; @@ -45,35 +55,36 @@ class Carrier extends AbstractCarrier implements \Magento\Shipping\Model\Carrier protected $_rateFactory; /** - * @var \Magento\Framework\App\State + * @var State */ protected $_state; /** - * @var \MagePal\CustomShippingRate\Helper\Data + * @var Data */ protected $_customShippingRateHelper; /** - * @param \Magento\Framework\App\Config\ScopeConfigInterface $scopeConfig - * @param \Magento\Quote\Model\Quote\Address\RateResult\ErrorFactory $rateErrorFactory - * @param \Psr\Log\LoggerInterface $logger + * @param ScopeConfigInterface $scopeConfig + * @param ErrorFactory $rateErrorFactory + * @param LoggerInterface $logger + * @param ResultFactory $rateFactory + * @param ShippingCarrierHelper $carrierHelper + * @param MethodFactory $rateMethodFactory + * @param State $state + * @param Data $customShippingRateHelper * @param array $data - * @param \Magento\Shipping\Model\Rate\ResultFactory $rateFactory - * @param \Magento\Shipping\Helper\Carrier $carrierHelper - * @param \Magento\Quote\Model\Quote\Address\RateResult\MethodFactory $rateMethodFactory - * * @SuppressWarnings(PHPMD.ExcessiveParameterList) */ public function __construct( - \Magento\Framework\App\Config\ScopeConfigInterface $scopeConfig, - \Magento\Quote\Model\Quote\Address\RateResult\ErrorFactory $rateErrorFactory, - \Psr\Log\LoggerInterface $logger, - \Magento\Shipping\Model\Rate\ResultFactory $rateFactory, - \Magento\Shipping\Helper\Carrier $carrierHelper, - \Magento\Quote\Model\Quote\Address\RateResult\MethodFactory $rateMethodFactory, - \Magento\Framework\App\State $state, - \MagePal\CustomShippingRate\Helper\Data $customShippingRateHelper, + ScopeConfigInterface $scopeConfig, + ErrorFactory $rateErrorFactory, + LoggerInterface $logger, + ResultFactory $rateFactory, + ShippingCarrierHelper $carrierHelper, + MethodFactory $rateMethodFactory, + State $state, + Data $customShippingRateHelper, array $data = [] ) { parent::__construct($scopeConfig, $rateErrorFactory, $logger, $data); @@ -91,13 +102,14 @@ public function __construct( * Collect and get rates * * @param RateRequest $request - * @return \Magento\Quote\Model\Quote\Address\RateResult\Error|bool|Result + * @return \Magento\Catalog\Model\ResourceModel\Product\Collection|\Magento\Shipping\Model\Rate\Result + * @throws \Magento\Framework\Exception\LocalizedException */ public function collectRates(RateRequest $request) { $result = $this->_rateFactory->create(); - if (!$this->getConfigFlag('active') || ($this->_state->getAreaCode() != \Magento\Backend\App\Area\FrontNameResolver::AREA_CODE && !$this->getConfigFlag('show_on_frontend'))) { + if (!$this->getConfigFlag('active') || (!$this->isAdmin() && $this->hideShippingMethodOnFrontend())) { return $result; } @@ -117,10 +129,10 @@ public function collectRates(RateRequest $request) } /** - * Get allowed shipping methods - * - * @return array - */ + * Get allowed shipping methods + * + * @return array + */ public function getAllowedMethods() { return [$this->getCarrierCode() => __($this->getConfigData('name'))]; @@ -130,4 +142,22 @@ public function isTrackingAvailable() { return false; } + + /** + * @return bool + * @throws \Magento\Framework\Exception\LocalizedException + */ + protected function hideShippingMethodOnFrontend() + { + return !$this->getConfigFlag('show_on_frontend'); + } + + /** + * @return bool + * @throws \Magento\Framework\Exception\LocalizedException + */ + protected function isAdmin() + { + return $this->_state->getAreaCode() == FrontNameResolver::AREA_CODE; + } } diff --git a/Plugin/Quote/Address/Total/ShippingPlugin.php b/Plugin/Quote/Address/Total/ShippingPlugin.php index e6449d2..661a077 100644 --- a/Plugin/Quote/Address/Total/ShippingPlugin.php +++ b/Plugin/Quote/Address/Total/ShippingPlugin.php @@ -7,19 +7,20 @@ namespace MagePal\CustomShippingRate\Plugin\Quote\Address\Total; +use Magento\Quote\Api\Data\ShippingAssignmentInterface; +use Magento\Quote\Model\Quote; +use Magento\Quote\Model\Quote\Address\Total; +use Magento\Quote\Model\Quote\Address\Total\Shipping; +use \MagePal\CustomShippingRate\Model\Carrier; +use \Magento\Quote\Model\Quote\Address; + class ShippingPlugin { - /** * @var \MagePal\CustomShippingRate\Helper\Data */ protected $_customShippingRateHelper; - /** - * @param \Magento\Quote\Model\Quote - */ - protected $_quote; - /** * @param \MagePal\CustomShippingRate\Helper\Data $customShippingRateHelper */ @@ -30,113 +31,113 @@ public function __construct( } /** - * @param \Magento\Quote\Model\Quote\Address\Total\Shipping $subject + * @param Shipping $subject * @param callable $proceed - * @param \Magento\Quote\Model\Quote $quote - * @param \Magento\Quote\Api\Data\ShippingAssignmentInterface $shippingAssignment - * @param \Magento\Quote\Model\Quote\Address\Total $total + * @param Quote $quote + * @param ShippingAssignmentInterface $shippingAssignment + * @param Total $total * @return mixed */ public function aroundCollect( - \Magento\Quote\Model\Quote\Address\Total\Shipping $subject, + Shipping $subject, callable $proceed, - \Magento\Quote\Model\Quote $quote, - \Magento\Quote\Api\Data\ShippingAssignmentInterface $shippingAssignment, - \Magento\Quote\Model\Quote\Address\Total $total + Quote $quote, + ShippingAssignmentInterface $shippingAssignment, + Total $total ) { - $returnValue = $proceed($quote, $shippingAssignment, $total); - if (!$this->_customShippingRateHelper->isEnabled()) { - return $returnValue; - } - - $this->setQuote($quote); - - $address = $shippingAssignment->getShipping()->getAddress(); - $method = $shippingAssignment->getShipping()->getMethod(); + $shipping = $shippingAssignment->getShipping(); + $address = $shipping->getAddress(); + $method = $address->getShippingMethod(); - if (strpos($method, \MagePal\CustomShippingRate\Model\Carrier::CODE) !== false) { - $customOption = $this->getCustomShippingJsonToArray($method); + if (!$this->_customShippingRateHelper->isEnabled() + || $address->getAddressType() != Address::ADDRESS_TYPE_SHIPPING + || strpos($method, Carrier::CODE) === false + ) { + return $proceed($quote, $shippingAssignment, $total); + } - if ($customOption && strpos($method, $customOption['code']) !== false) { - foreach ($address->getAllShippingRates() as $rate) { - if ($rate->getCode() == $customOption['code']) { - $cost = $customOption['rate']; - $description = trim($customOption['description']); + $customShippingOption = $this->getCustomShippingJsonToArray($method, $address); - //Empty by default. Use in third-party modules - if (empty($description) || strlen($description) < 2) { - $description = $rate->getCarrierTitle() . ' - ' . $rate->getMethodTitle(); - } + if ($customShippingOption && strpos($method, $customShippingOption['code']) !== false) { + //update shipping code + $shipping->setMethod($customShippingOption['code']); + $address->setShippingMethod($customShippingOption['code']); + $this->updateCustomRate($address, $customShippingOption); + } - $rate->setPrice($cost); - $rate->setMethodTitle($description); - $address->setShippingMethod($customOption['code']); - $address->setShippingAmount($cost); - $address->setBaseShippingAmount($cost); - $address->setShippingDescription($description); - $total->setShippingAmount($cost); - $total->setBaseShippingAmount($cost); + return $proceed($quote, $shippingAssignment, $total); + } - break; - } + /** + * @param $address + * @param $customShippingOption + */ + protected function updateCustomRate($address, $customShippingOption) + { + foreach ($address->getAllShippingRates() as $rate) { + if ($rate->getCode() == $customShippingOption['code']) { + $cost = (float) $customShippingOption['rate']; + $description = trim($customShippingOption['description']); + + $address->setShippingAmount($cost); + $rate->setPrice($cost); + //Empty by default. Use in third-party modules + if (!empty($description) || strlen($description) > 2) { + $rate->setMethodTitle($description); } + + break; } } - - return $returnValue; } /** * @param $json + * @param $address * @return array|bool */ - private function getCustomShippingJsonToArray($json) + private function getCustomShippingJsonToArray($json, $address) { - $customOption = [ - 'code' => '', - 'rate' => 0, - 'type' => '', - 'description' => '' - ]; - - $jsonToArray = (array)json_decode($json, true); + $isJson = $this->_customShippingRateHelper->isJson($json); - if (!$json || count($jsonToArray) != 4) { - $json = $this->getQuote()->getCustomShippingRateJson(); + //reload exist shipping cost if custom shipping method + if ($json && !$isJson) { + $jsonToArray = [ + 'code' => $json, + 'type' => $this->_customShippingRateHelper->getShippingCodeFromMethod($json), + 'rate' => $address->getShippingAmount() + ]; - if ($json) { - $jsonToArray = (array)json_decode($json, true); - } + return $this->formatShippingArray($jsonToArray); } - if (is_array($jsonToArray) && count($jsonToArray) == 4) { - foreach ($jsonToArray as $key => $value) { - $customOption[$key] = $value; - } + $jsonToArray = (array)json_decode($json, true); - $this->getQuote()->setCustomShippingRateJson($json); - return $customOption; + if (is_array($jsonToArray) && count($jsonToArray) == 4) { + return $this->formatShippingArray($jsonToArray); } return false; } /** - * @param mixed $quote - * @return ShippingPlugin + * @param $jsonToArray array + * @return array */ - public function setQuote($quote) + protected function formatShippingArray($jsonToArray) { - $this->_quote = $quote; - return $this; - } + $customShippingOption = [ + 'code' => '', + 'rate' => 0, + 'type' => '', + 'description' => '' + ]; - /** - * @return \Magento\Quote\Model\Quote - */ - public function getQuote() - { - return $this->_quote; + foreach ((array) $jsonToArray as $key => $value) { + $customShippingOption[$key] = $value; + } + + return $customShippingOption; } } diff --git a/composer.json b/composer.json index 199a9bb..b7a220a 100644 --- a/composer.json +++ b/composer.json @@ -16,7 +16,7 @@ "magento 2 free shipping extension" ], "type": "magento2-module", - "version": "1.4.2", + "version": "1.5.0", "license": [ "proprietary" ], diff --git a/etc/adminhtml/system.xml b/etc/adminhtml/system.xml index 9ae1a8f..bfbc61b 100644 --- a/etc/adminhtml/system.xml +++ b/etc/adminhtml/system.xml @@ -67,6 +67,16 @@ shipping-skip-hide Magento\Config\Model\Config\Source\Yesno + + + shipping-applicable-country + Magento\Shipping\Model\Config\Source\Allspecificcountries + + + + Magento\Directory\Model\Config\Source\Country + 1 + diff --git a/etc/di.xml b/etc/di.xml new file mode 100644 index 0000000..36264ec --- /dev/null +++ b/etc/di.xml @@ -0,0 +1,8 @@ + + + + + + + \ No newline at end of file