12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091929394959697989910010110210310410510610710810911011111211311411511611711811912012112212312412512612712812913013113213313413513613713813914014114214314414514614714814915015115215315415515615715815916016116216316416516616716816917017117217317417517617717817918018118218318418518618718818919019119219319419519619719819920020120220320420520620720820921021121221321421521621721821922022122222322422522622722822923023123223323423523623723823924024124224324424524624724824925025125225325425525625725825926026126226326426526626726826927027127227327427527627727827928028128228328428528628728828929029129229329429529629729829930030130230330430530630730830931031131231331431531631731831932032132232332432532632732832933033133233333433533633733833934034134234334434534634734834935035135235335435535635735835936036136236336436536636736836937037137237337437537637737837938038138238338438538638738838939039139239339439539639739839940040140240340440540640740840941041141241341441541641741841942042142242342442542642742842943043143243343443543643743843944044144244344444544644744844945045145245345445545645745845946046146246346446546646746846947047147247347447547647747847948048148248348448548648748848949049149249349449549649749849950050150250350450550650750850951051151251351451551651751851952052152252352452552652752852953053153253353453553653753853954054154254354454554654754854955055155255355455555655755855956056156256356456556656756856957057157257357457557657757857958058158258358458558658758858959059159259359459559659759859960060160260360460560660760860961061161261361461561661761861962062162262362462562662762862963063163263363463563663763863964064164264364464564664764864965065165265365465565665765865966066166266366466566666766866967067167267367467567667767867968068168268368468568668768868969069169269369469569669769869970070170270370470570670770870971071171271371471571671771871972072172272372472572672772872973073173273373473573673773873974074174274374474574674774874975075175275375475575675775875976076176276376476576676776876977077177277377477577677777877978078178278378478578678778878979079179279379479579679779879980080180280380480580680780880981081181281381481581681781881982082182282382482582682782882983083183283383483583683783883984084184284384484584684784884985085185285385485585685785885986086186286386486586686786886987087187287387487587687787887988088188288388488588688788888989089189289389489589689789889990090190290390490590690790890991091191291391491591691791891992092192292392492592692792892993093193293393493593693793893994094194294394494594694794894995095195295395495595695795895996096196296396496596696796896997097197297397497597697797897998098198298398498598698798898999099199299399499599699799899910001001100210031004100510061007100810091010101110121013101410151016101710181019102010211022102310241025102610271028102910301031103210331034103510361037103810391040104110421043104410451046104710481049105010511052105310541055105610571058105910601061106210631064106510661067106810691070107110721073107410751076107710781079108010811082108310841085108610871088108910901091109210931094109510961097109810991100110111021103110411051106110711081109111011111112111311141115111611171118111911201121112211231124112511261127112811291130113111321133113411351136113711381139114011411142114311441145114611471148114911501151115211531154115511561157115811591160116111621163116411651166116711681169117011711172117311741175117611771178117911801181118211831184118511861187118811891190119111921193119411951196119711981199120012011202120312041205120612071208120912101211121212131214121512161217121812191220122112221223122412251226122712281229123012311232123312341235123612371238123912401241124212431244124512461247124812491250125112521253125412551256125712581259126012611262126312641265126612671268126912701271127212731274127512761277127812791280128112821283128412851286128712881289129012911292129312941295129612971298129913001301130213031304130513061307130813091310131113121313131413151316131713181319132013211322132313241325132613271328132913301331133213331334133513361337133813391340134113421343134413451346134713481349135013511352135313541355135613571358135913601361136213631364136513661367136813691370137113721373137413751376137713781379138013811382138313841385138613871388138913901391139213931394139513961397139813991400140114021403140414051406140714081409141014111412141314141415141614171418141914201421142214231424142514261427142814291430143114321433143414351436143714381439144014411442144314441445144614471448144914501451145214531454145514561457145814591460146114621463146414651466146714681469147014711472147314741475147614771478147914801481148214831484148514861487148814891490149114921493149414951496149714981499150015011502150315041505150615071508150915101511151215131514151515161517151815191520152115221523152415251526152715281529153015311532153315341535153615371538153915401541154215431544154515461547154815491550155115521553155415551556155715581559156015611562156315641565156615671568156915701571157215731574157515761577157815791580158115821583158415851586158715881589159015911592159315941595159615971598159916001601160216031604160516061607160816091610161116121613161416151616161716181619162016211622162316241625162616271628162916301631163216331634163516361637163816391640164116421643164416451646164716481649165016511652165316541655165616571658165916601661166216631664166516661667166816691670167116721673167416751676167716781679168016811682168316841685168616871688168916901691169216931694169516961697169816991700170117021703170417051706170717081709171017111712171317141715171617171718171917201721172217231724172517261727172817291730173117321733173417351736173717381739174017411742174317441745174617471748174917501751175217531754175517561757175817591760176117621763176417651766176717681769177017711772177317741775177617771778177917801781178217831784178517861787178817891790179117921793179417951796179717981799180018011802180318041805180618071808180918101811181218131814181518161817181818191820182118221823182418251826182718281829183018311832183318341835183618371838183918401841184218431844184518461847184818491850185118521853185418551856185718581859186018611862186318641865186618671868186918701871187218731874187518761877187818791880188118821883188418851886188718881889189018911892189318941895189618971898189919001901190219031904190519061907190819091910191119121913191419151916191719181919192019211922192319241925192619271928192919301931193219331934193519361937193819391940194119421943194419451946194719481949195019511952195319541955195619571958195919601961196219631964196519661967196819691970197119721973197419751976197719781979198019811982198319841985198619871988198919901991199219931994199519961997199819992000200120022003200420052006200720082009201020112012201320142015201620172018201920202021202220232024202520262027202820292030203120322033203420352036203720382039204020412042204320442045204620472048204920502051205220532054205520562057205820592060206120622063206420652066206720682069207020712072207320742075207620772078207920802081208220832084208520862087208820892090209120922093209420952096209720982099210021012102210321042105210621072108210921102111211221132114211521162117211821192120212121222123212421252126212721282129213021312132213321342135213621372138213921402141214221432144214521462147214821492150215121522153215421552156215721582159216021612162216321642165216621672168216921702171217221732174217521762177217821792180218121822183218421852186218721882189219021912192219321942195219621972198219922002201220222032204220522062207220822092210221122122213221422152216221722182219222022212222222322242225222622272228222922302231223222332234223522362237223822392240224122422243224422452246224722482249225022512252225322542255225622572258225922602261226222632264226522662267226822692270227122722273227422752276227722782279228022812282228322842285228622872288228922902291229222932294229522962297229822992300230123022303230423052306230723082309231023112312231323142315231623172318231923202321232223232324232523262327232823292330233123322333233423352336233723382339234023412342234323442345234623472348234923502351235223532354235523562357235823592360236123622363236423652366236723682369237023712372237323742375237623772378237923802381238223832384238523862387238823892390239123922393239423952396239723982399240024012402240324042405240624072408240924102411241224132414241524162417241824192420242124222423242424252426242724282429243024312432243324342435243624372438243924402441244224432444244524462447244824492450245124522453245424552456245724582459246024612462246324642465246624672468246924702471247224732474247524762477247824792480248124822483248424852486248724882489249024912492249324942495249624972498249925002501250225032504250525062507250825092510251125122513251425152516251725182519252025212522252325242525252625272528252925302531253225332534253525362537253825392540254125422543254425452546254725482549255025512552255325542555255625572558255925602561256225632564256525662567256825692570257125722573 |
- <?php
- /**
- * Copyright © Magento, Inc. All rights reserved.
- * See COPYING.txt for license details.
- */
- namespace Magento\Sales\Model\Order;
- use Magento\Framework\App\ObjectManager;
- use Magento\Framework\Pricing\PriceCurrencyInterface;
- use Magento\Sales\Api\Data\OrderPaymentInterface;
- use Magento\Sales\Api\OrderRepositoryInterface;
- use Magento\Sales\Model\Order;
- use Magento\Sales\Model\Order\Payment\Info;
- use Magento\Sales\Model\Order\Payment\Transaction;
- use Magento\Sales\Model\Order\Payment\Transaction\ManagerInterface;
- use Magento\Sales\Api\CreditmemoManagementInterface as CreditmemoManager;
- /**
- * Order payment information
- *
- * @api
- * @SuppressWarnings(PHPMD.ExcessivePublicCount)
- * @SuppressWarnings(PHPMD.ExcessiveClassComplexity)
- * @SuppressWarnings(PHPMD.CouplingBetweenObjects)
- * @since 100.0.2
- */
- class Payment extends Info implements OrderPaymentInterface
- {
- /**
- * Actions for payment when it triggered review state
- *
- * @var string
- */
- const REVIEW_ACTION_ACCEPT = 'accept';
- const REVIEW_ACTION_DENY = 'deny';
- const REVIEW_ACTION_UPDATE = 'update';
- const PARENT_TXN_ID = 'parent_transaction_id';
- /**
- * Order model object
- *
- * @var Order
- */
- protected $_order;
- /**
- * Whether can void
- * @var string
- */
- protected $_canVoidLookup = null;
- /**
- * @var string
- */
- protected $_eventPrefix = 'sales_order_payment';
- /**
- * @var string
- */
- protected $_eventObject = 'payment';
- /**
- * Transaction additional information container
- *
- * @var array
- */
- protected $transactionAdditionalInfo = [];
- /**
- * @var \Magento\Sales\Model\Order\CreditmemoFactory
- */
- protected $creditmemoFactory;
- /**
- * @var PriceCurrencyInterface
- */
- protected $priceCurrency;
- /**
- * @var \Magento\Sales\Api\TransactionRepositoryInterface
- */
- protected $transactionRepository;
- /**
- * @var \Magento\Sales\Model\Order\Payment\Transaction\ManagerInterface
- */
- protected $transactionManager;
- /**
- * @var \Magento\Sales\Model\Order\Payment\Transaction\BuilderInterface
- */
- protected $transactionBuilder;
- /**
- * @var Payment\Processor
- */
- protected $orderPaymentProcessor;
- /**
- * @var OrderRepositoryInterface
- */
- protected $orderRepository;
- /**
- * @var OrderStateResolverInterface
- */
- private $orderStateResolver;
- /**
- * @var CreditmemoManager
- */
- private $creditmemoManager = null;
- /**
- * @param \Magento\Framework\Model\Context $context
- * @param \Magento\Framework\Registry $registry
- * @param \Magento\Framework\Api\ExtensionAttributesFactory $extensionFactory
- * @param \Magento\Framework\Api\AttributeValueFactory $customAttributeFactory
- * @param \Magento\Payment\Helper\Data $paymentData
- * @param \Magento\Framework\Encryption\EncryptorInterface $encryptor
- * @param \Magento\Sales\Model\Order\CreditmemoFactory $creditmemoFactory
- * @param PriceCurrencyInterface $priceCurrency
- * @param \Magento\Sales\Api\TransactionRepositoryInterface $transactionRepository
- * @param \Magento\Sales\Model\Order\Payment\Transaction\ManagerInterface $transactionManager
- * @param Transaction\BuilderInterface $transactionBuilder
- * @param Payment\Processor $paymentProcessor
- * @param OrderRepositoryInterface $orderRepository
- * @param \Magento\Framework\Model\ResourceModel\AbstractResource $resource
- * @param \Magento\Framework\Data\Collection\AbstractDb $resourceCollection
- * @param array $data
- * @param CreditmemoManager $creditmemoManager
- * @SuppressWarnings(PHPMD.ExcessiveParameterList)
- */
- public function __construct(
- \Magento\Framework\Model\Context $context,
- \Magento\Framework\Registry $registry,
- \Magento\Framework\Api\ExtensionAttributesFactory $extensionFactory,
- \Magento\Framework\Api\AttributeValueFactory $customAttributeFactory,
- \Magento\Payment\Helper\Data $paymentData,
- \Magento\Framework\Encryption\EncryptorInterface $encryptor,
- \Magento\Sales\Model\Order\CreditmemoFactory $creditmemoFactory,
- PriceCurrencyInterface $priceCurrency,
- \Magento\Sales\Api\TransactionRepositoryInterface $transactionRepository,
- ManagerInterface $transactionManager,
- \Magento\Sales\Model\Order\Payment\Transaction\BuilderInterface $transactionBuilder,
- \Magento\Sales\Model\Order\Payment\Processor $paymentProcessor,
- OrderRepositoryInterface $orderRepository,
- \Magento\Framework\Model\ResourceModel\AbstractResource $resource = null,
- \Magento\Framework\Data\Collection\AbstractDb $resourceCollection = null,
- array $data = [],
- CreditmemoManager $creditmemoManager = null
- ) {
- $this->priceCurrency = $priceCurrency;
- $this->creditmemoFactory = $creditmemoFactory;
- $this->transactionRepository = $transactionRepository;
- $this->transactionManager = $transactionManager;
- $this->transactionBuilder = $transactionBuilder;
- $this->orderPaymentProcessor = $paymentProcessor;
- $this->orderRepository = $orderRepository;
- $this->creditmemoManager = $creditmemoManager ?: ObjectManager::getInstance()->get(CreditmemoManager::class);
- parent::__construct(
- $context,
- $registry,
- $extensionFactory,
- $customAttributeFactory,
- $paymentData,
- $encryptor,
- $resource,
- $resourceCollection,
- $data
- );
- }
- /**
- * Initialize resource model
- *
- * @return void
- */
- protected function _construct()
- {
- $this->_init(\Magento\Sales\Model\ResourceModel\Order\Payment::class);
- }
- /**
- * Declare order model object
- *
- * @codeCoverageIgnore
- *
- * @param Order $order
- * @return $this
- */
- public function setOrder(Order $order)
- {
- $this->_order = $order;
- return $this;
- }
- /**
- * Retrieve order model object
- *
- * @codeCoverageIgnore
- * @return Order
- */
- public function getOrder()
- {
- if (!$this->_order && $this->getParentId()) {
- $this->_order = $this->orderRepository->get($this->getParentId());
- }
- return $this->_order;
- }
- /**
- * Sets transaction id for current payment
- *
- * @param string $transactionId
- * @return $this
- */
- public function setTransactionId($transactionId)
- {
- $this->setData('transaction_id', $transactionId);
- return $this;
- }
- /**
- * Return transaction id
- *
- * @return int
- */
- public function getTransactionId()
- {
- return $this->getData('transaction_id');
- }
- /**
- * Sets transaction close flag
- *
- * @param bool $isClosed
- * @return $this
- */
- public function setIsTransactionClosed($isClosed)
- {
- $this->setData('is_transaction_closed', (bool)$isClosed);
- return $this;
- }
- /**
- * Returns transaction parent
- *
- * @return string
- */
- public function getParentTransactionId()
- {
- return $this->getData(self::PARENT_TXN_ID);
- }
- /**
- * Returns transaction parent
- *
- * @param string $txnId
- * @return string
- * @since 100.1.0
- */
- public function setParentTransactionId($txnId)
- {
- return $this->setData(self::PARENT_TXN_ID, $txnId);
- }
- /**
- * Check order payment capture action availability
- *
- * @return bool
- */
- public function canCapture()
- {
- if (!$this->getMethodInstance()->canCapture()) {
- return false;
- }
- // Check Authorization transaction state
- $authTransaction = $this->getAuthorizationTransaction();
- if ($authTransaction && $authTransaction->getIsClosed()) {
- $orderTransaction = $this->transactionRepository->getByTransactionType(
- Transaction::TYPE_ORDER,
- $this->getId(),
- $this->getOrder()->getId()
- );
- if (!$orderTransaction) {
- return false;
- }
- }
- return true;
- }
- /**
- * Check refund availability
- *
- * @return bool
- */
- public function canRefund()
- {
- return $this->getMethodInstance()->canRefund();
- }
- /**
- * Check partial refund availability for invoice
- *
- * @return bool
- */
- public function canRefundPartialPerInvoice()
- {
- return $this->getMethodInstance()->canRefundPartialPerInvoice();
- }
- /**
- * Check partial capture availability
- *
- * @return bool
- */
- public function canCapturePartial()
- {
- return $this->getMethodInstance()->canCapturePartial();
- }
- /**
- * Authorize or authorize and capture payment on gateway, if applicable
- *
- * This method is supposed to be called only when order is placed
- *
- * @return $this
- * @SuppressWarnings(PHPMD.NPathComplexity)
- * @SuppressWarnings(PHPMD.CyclomaticComplexity)
- */
- public function place()
- {
- $this->_eventManager->dispatch('sales_order_payment_place_start', ['payment' => $this]);
- $order = $this->getOrder();
- $this->setAmountOrdered($order->getTotalDue());
- $this->setBaseAmountOrdered($order->getBaseTotalDue());
- $this->setShippingAmount($order->getShippingAmount());
- $this->setBaseShippingAmount($order->getBaseShippingAmount());
- $methodInstance = $this->getMethodInstance();
- $methodInstance->setStore($order->getStoreId());
- $orderState = Order::STATE_NEW;
- $orderStatus = $methodInstance->getConfigData('order_status');
- $isCustomerNotified = $order->getCustomerNoteNotify();
- // Do order payment validation on payment method level
- $methodInstance->validate();
- $action = $methodInstance->getConfigPaymentAction();
- if ($action) {
- if ($methodInstance->isInitializeNeeded()) {
- $stateObject = new \Magento\Framework\DataObject();
- // For method initialization we have to use original config value for payment action
- $methodInstance->initialize($methodInstance->getConfigData('payment_action'), $stateObject);
- $orderState = $stateObject->getData('state') ?: $orderState;
- $orderStatus = $stateObject->getData('status') ?: $orderStatus;
- $isCustomerNotified = $stateObject->hasData('is_notified')
- ? $stateObject->getData('is_notified')
- : $isCustomerNotified;
- } else {
- $orderState = Order::STATE_PROCESSING;
- $this->processAction($action, $order);
- $orderState = $order->getState() ? $order->getState() : $orderState;
- $orderStatus = $order->getStatus() ? $order->getStatus() : $orderStatus;
- }
- } else {
- $order->setState($orderState)
- ->setStatus($orderStatus);
- }
- $isCustomerNotified = $isCustomerNotified ?: $order->getCustomerNoteNotify();
- if (!array_key_exists($orderStatus, $order->getConfig()->getStateStatuses($orderState))) {
- $orderStatus = $order->getConfig()->getStateDefaultStatus($orderState);
- }
- $this->updateOrder($order, $orderState, $orderStatus, $isCustomerNotified);
- $this->_eventManager->dispatch('sales_order_payment_place_end', ['payment' => $this]);
- return $this;
- }
- /**
- * Set appropriate state to order or add status to order history
- *
- * @param Order $order
- * @param string $orderState
- * @param string $orderStatus
- * @param bool $isCustomerNotified
- * @return void
- */
- protected function updateOrder(Order $order, $orderState, $orderStatus, $isCustomerNotified)
- {
- // add message if order was put into review during authorization or capture
- $message = $order->getCustomerNote();
- $originalOrderState = $order->getState();
- $originalOrderStatus = $order->getStatus();
- switch (true) {
- case ($message && ($originalOrderState == Order::STATE_PAYMENT_REVIEW)):
- $order->addStatusToHistory($originalOrderStatus, $message, $isCustomerNotified);
- break;
- case ($message):
- case ($originalOrderState && $message):
- case ($originalOrderState != $orderState):
- case ($originalOrderStatus != $orderStatus):
- $order->setState($orderState)
- ->setStatus($orderStatus)
- ->addStatusHistoryComment($message)
- ->setIsCustomerNotified($isCustomerNotified);
- break;
- default:
- break;
- }
- }
- /**
- * Perform actions based on passed action name
- *
- * @param string $action
- * @param Order $order
- * @return void
- */
- protected function processAction($action, Order $order)
- {
- $totalDue = $order->getTotalDue();
- $baseTotalDue = $order->getBaseTotalDue();
- switch ($action) {
- case \Magento\Payment\Model\Method\AbstractMethod::ACTION_ORDER:
- $this->_order($baseTotalDue);
- break;
- case \Magento\Payment\Model\Method\AbstractMethod::ACTION_AUTHORIZE:
- $this->authorize(true, $baseTotalDue);
- // base amount will be set inside
- $this->setAmountAuthorized($totalDue);
- break;
- case \Magento\Payment\Model\Method\AbstractMethod::ACTION_AUTHORIZE_CAPTURE:
- $this->setAmountAuthorized($totalDue);
- $this->setBaseAmountAuthorized($baseTotalDue);
- $this->capture(null);
- break;
- default:
- break;
- }
- }
- /**
- * Capture the payment online
- * Requires an invoice. If there is no invoice specified, will automatically prepare an invoice for order
- * Updates transactions hierarchy, if required
- * Updates payment totals, updates order status and adds proper comments
- *
- * @param null|Invoice $invoice
- * @throws \Magento\Framework\Exception\LocalizedException
- * @return $this
- */
- public function capture($invoice = null)
- {
- return $this->orderPaymentProcessor->capture($this, $invoice);
- }
- /**
- * Process a capture notification from a payment gateway for specified amount
- * Creates an invoice automatically if the amount covers the order base grand total completely
- * Updates transactions hierarchy, if required
- * Prevents transaction double processing
- * Updates payment totals, updates order status and adds proper comments
- *
- * @param float $amount
- * @param bool $skipFraudDetection
- * @return $this
- */
- public function registerCaptureNotification($amount, $skipFraudDetection = false)
- {
- return $this->orderPaymentProcessor->registerCaptureNotification($this, $amount, $skipFraudDetection);
- }
- /**
- * Process authorization notification
- *
- * @param float $amount
- * @return $this
- * @see self::_authorize()
- */
- public function registerAuthorizationNotification($amount)
- {
- return $this->checkIfTransactionExists() ? $this : $this->authorize(false, $amount);
- }
- /**
- * Register payment fact: update self totals from the invoice
- *
- * @param Invoice $invoice
- * @return $this
- */
- public function pay($invoice)
- {
- $totals = $this->collectTotalAmounts(
- $this->getOrder(),
- ['grand_total', 'base_grand_total', 'shipping_amount', 'base_shipping_amount']
- );
- $this->setAmountPaid($totals['grand_total']);
- $this->setBaseAmountPaid($totals['base_grand_total']);
- $this->setShippingCaptured($totals['shipping_amount']);
- $this->setBaseShippingCaptured($totals['base_shipping_amount']);
- $this->_eventManager->dispatch('sales_order_payment_pay', ['payment' => $this, 'invoice' => $invoice]);
- return $this;
- }
- /**
- * Cancel specified invoice: update self totals from it
- *
- * @param Invoice $invoice
- * @return $this
- */
- public function cancelInvoice($invoice)
- {
- $this->_updateTotals(
- [
- 'amount_paid' => -1 * $invoice->getGrandTotal(),
- 'base_amount_paid' => -1 * $invoice->getBaseGrandTotal(),
- 'shipping_captured' => -1 * $invoice->getShippingAmount(),
- 'base_shipping_captured' => -1 * $invoice->getBaseShippingAmount(),
- ]
- );
- $this->_eventManager->dispatch(
- 'sales_order_payment_cancel_invoice',
- ['payment' => $this, 'invoice' => $invoice]
- );
- return $this;
- }
- /**
- * Create new invoice with maximum qty for invoice for each item
- *
- * Register this invoice and capture
- *
- * @return Invoice
- */
- protected function _invoice()
- {
- $invoice = $this->getOrder()->prepareInvoice();
- $invoice->register();
- if ($this->getMethodInstance()->canCapture()) {
- $invoice->capture();
- }
- $this->getOrder()->addRelatedObject($invoice);
- return $invoice;
- }
- /**
- * Check order payment void availability
- *
- * @return bool
- */
- public function canVoid()
- {
- if (null === $this->_canVoidLookup) {
- $this->_canVoidLookup = (bool)$this->getMethodInstance()->canVoid();
- if ($this->_canVoidLookup) {
- $authTransaction = $this->getAuthorizationTransaction();
- $this->_canVoidLookup = (bool)$authTransaction && !(int)$authTransaction->getIsClosed();
- }
- }
- return $this->_canVoidLookup;
- }
- /**
- * Void payment online
- *
- * @param \Magento\Framework\DataObject $document
- * @return $this
- * @see self::_void()
- */
- public function void(\Magento\Framework\DataObject $document)
- {
- $this->_void(true);
- $this->_eventManager->dispatch('sales_order_payment_void', ['payment' => $this, 'invoice' => $document]);
- return $this;
- }
- /**
- * Process void notification
- *
- * @param float $amount
- * @return $this
- * @see self::_void()
- */
- public function registerVoidNotification($amount = null)
- {
- if (!$this->hasMessage()) {
- $this->setMessage(__('Registered a Void notification.'));
- }
- return $this->_void(false, $amount);
- }
- /**
- * Sets creditmemo for current payment
- *
- * @param Creditmemo $creditmemo
- * @return $this
- */
- public function setCreditmemo(Creditmemo $creditmemo)
- {
- $this->setData('creditmemo', $creditmemo);
- return $this;
- }
- /**
- * Returns Creditmemo assigned for this payment
- *
- * @return Creditmemo|null
- */
- public function getCreditmemo()
- {
- return $this->getData('creditmemo') instanceof Creditmemo
- ? $this->getData('creditmemo')
- : null;
- }
- /**
- * Refund payment online or offline, depending on whether there is invoice set in the creditmemo instance
- * Updates transactions hierarchy, if required
- * Updates payment totals, updates order status and adds proper comments
- *
- * @param Creditmemo $creditmemo
- * @return $this
- * @throws \Exception
- * @throws \Magento\Framework\Exception\LocalizedException
- * @SuppressWarnings(PHPMD.CyclomaticComplexity)
- * @SuppressWarnings(PHPMD.NPathComplexity)
- */
- public function refund($creditmemo)
- {
- $baseAmountToRefund = $this->formatAmount($creditmemo->getBaseGrandTotal());
- $this->setTransactionId(
- $this->transactionManager->generateTransactionId($this, Transaction::TYPE_REFUND)
- );
- $isOnline = false;
- $gateway = $this->getMethodInstance();
- $invoice = null;
- if ($gateway->canRefund()) {
- $this->setCreditmemo($creditmemo);
- if ($creditmemo->getDoTransaction()) {
- $invoice = $creditmemo->getInvoice();
- if ($invoice) {
- $isOnline = true;
- $captureTxn = $this->transactionRepository->getByTransactionId(
- $invoice->getTransactionId(),
- $this->getId(),
- $this->getOrder()->getId()
- );
- if ($captureTxn) {
- $this->setTransactionIdsForRefund($captureTxn);
- }
- $this->setShouldCloseParentTransaction(true);
- // TODO: implement multiple refunds per capture
- try {
- $gateway->setStore(
- $this->getOrder()->getStoreId()
- );
- $this->setRefundTransactionId($invoice->getTransactionId());
- $gateway->refund($this, $baseAmountToRefund);
- $creditmemo->setTransactionId($this->getLastTransId());
- } catch (\Magento\Framework\Exception\LocalizedException $e) {
- if (!$captureTxn) {
- throw new \Magento\Framework\Exception\LocalizedException(
- __('If the invoice was created offline, try creating an offline credit memo.'),
- $e
- );
- }
- throw $e;
- }
- }
- } elseif ($gateway->isOffline()) {
- $gateway->setStore(
- $this->getOrder()->getStoreId()
- );
- $gateway->refund($this, $baseAmountToRefund);
- }
- }
- // update self totals from creditmemo
- $this->_updateTotals(
- [
- 'amount_refunded' => $creditmemo->getGrandTotal(),
- 'base_amount_refunded' => $baseAmountToRefund,
- 'base_amount_refunded_online' => $isOnline ? $baseAmountToRefund : null,
- 'shipping_refunded' => $creditmemo->getShippingAmount(),
- 'base_shipping_refunded' => $creditmemo->getBaseShippingAmount(),
- ]
- );
- // update transactions and order state
- $transaction = $this->addTransaction(
- Transaction::TYPE_REFUND,
- $creditmemo,
- $isOnline
- );
- if ($invoice) {
- $message = __('We refunded %1 online.', $this->formatPrice($baseAmountToRefund));
- } else {
- $message = $this->hasMessage() ? $this->getMessage() : __(
- 'We refunded %1 offline.',
- $this->formatPrice($baseAmountToRefund)
- );
- }
- $message = $message = $this->prependMessage($message);
- $message = $this->_appendTransactionToMessage($transaction, $message);
- $orderState = $this->getOrderStateResolver()->getStateForOrder($this->getOrder());
- $this->getOrder()
- ->addStatusHistoryComment(
- $message,
- $this->getOrder()->getConfig()->getStateDefaultStatus($orderState)
- )->setIsCustomerNotified($creditmemo->getOrder()->getCustomerNoteNotify());
- $this->_eventManager->dispatch(
- 'sales_order_payment_refund',
- ['payment' => $this, 'creditmemo' => $creditmemo]
- );
- return $this;
- }
- /**
- * Process payment refund notification
- * Updates transactions hierarchy, if required
- * Prevents transaction double processing
- * Updates payment totals, updates order status and adds proper comments
- * TODO: potentially a full capture can be refunded. In this case if there was only one invoice for that transaction
- * then we should create a creditmemo from invoice and also refund it offline
- * TODO: implement logic of chargebacks reimbursements (via negative amount)
- *
- * @param float $amount
- * @return $this
- * @SuppressWarnings(PHPMD.CyclomaticComplexity)
- */
- public function registerRefundNotification($amount)
- {
- $notificationAmount = $amount;
- $this->setTransactionId(
- $this->transactionManager->generateTransactionId(
- $this,
- Transaction::TYPE_REFUND,
- $this->transactionRepository->getByTransactionId(
- $this->getParentTransactionId(),
- $this->getId(),
- $this->getOrder()->getId()
- )
- )
- );
- if ($this->checkIfTransactionExists()) {
- return $this;
- }
- $order = $this->getOrder();
- $invoice = $this->_getInvoiceForTransactionId($this->getParentTransactionId());
- //choose where we get totals
- $salesEntity = $invoice ?: $order;
- $baseGrandTotal = $salesEntity->getBaseGrandTotal();
- $amountRefundLeft = $baseGrandTotal - $salesEntity->getBaseTotalRefunded();
- if ($amountRefundLeft < $amount) {
- $amount = $amountRefundLeft;
- }
- if ($amount != $baseGrandTotal) {
- $order->addStatusHistoryComment(
- __(
- 'IPN "Refunded". Refund issued by merchant. '
- . 'Registered notification about refunded amount of %1. Transaction ID: "%2". '
- . 'Credit Memo has not been created. Please create offline Credit Memo.',
- $this->formatPrice($notificationAmount),
- $this->getTransactionId()
- ),
- false
- );
- return $this;
- }
- $creditmemo = $this->prepareCreditMemo($amount, $baseGrandTotal, $invoice);
- $creditmemo->setPaymentRefundDisallowed(
- true
- )->setAutomaticallyCreated(
- true
- )->addComment(
- __('The credit memo has been created automatically.')
- );
- $this->creditmemoManager->refund($creditmemo, false);
- $this->_updateTotals(
- ['amount_refunded' => $creditmemo->getGrandTotal(), 'base_amount_refunded_online' => $amount]
- );
- $this->setCreatedCreditmemo($creditmemo);
- // update transactions and order state
- $transaction = $this->addTransaction(
- Transaction::TYPE_REFUND,
- $creditmemo
- );
- $message = $this->prependMessage(
- __('Registered notification about refunded amount of %1.', $this->formatPrice($amount))
- );
- $message = $this->_appendTransactionToMessage($transaction, $message);
- $this->setOrderStateProcessing($message);
- return $this;
- }
- /**
- * Cancel a creditmemo: substract its totals from the payment
- *
- * @param Creditmemo $creditmemo
- * @return $this
- */
- public function cancelCreditmemo($creditmemo)
- {
- $this->_updateTotals(
- [
- 'amount_refunded' => -1 * $creditmemo->getGrandTotal(),
- 'base_amount_refunded' => -1 * $creditmemo->getBaseGrandTotal(),
- 'shipping_refunded' => -1 * $creditmemo->getShippingAmount(),
- 'base_shipping_refunded' => -1 * $creditmemo->getBaseShippingAmount(),
- ]
- );
- $this->_eventManager->dispatch(
- 'sales_order_payment_cancel_creditmemo',
- ['payment' => $this, 'creditmemo' => $creditmemo]
- );
- return $this;
- }
- /**
- * Order cancellation hook for payment method instance
- *
- * Adds void transaction if needed
- *
- * @return $this
- */
- public function cancel()
- {
- $isOnline = true;
- if (!$this->canVoid()) {
- $isOnline = false;
- }
- if (!$this->hasMessage()) {
- $this->setMessage($isOnline ? __('Canceled order online') : __('Canceled order offline'));
- }
- if ($isOnline) {
- $this->_void($isOnline, null, 'cancel');
- }
- $this->_eventManager->dispatch('sales_order_payment_cancel', ['payment' => $this]);
- return $this;
- }
- /**
- * Check order payment review availability
- *
- * @return bool
- */
- public function canReviewPayment()
- {
- return (bool)$this->getMethodInstance()->canReviewPayment();
- }
- /**
- * Check fetch transaction info availability
- *
- * @return bool
- */
- public function canFetchTransactionInfo()
- {
- return (bool)$this->getMethodInstance()->canFetchTransactionInfo();
- }
- /**
- * Accept online a payment that is in review state
- *
- * @return $this
- */
- public function accept()
- {
- $transactionId = $this->getLastTransId();
- /** @var \Magento\Payment\Model\Method\AbstractMethod $method */
- $method = $this->getMethodInstance();
- $method->setStore($this->getOrder()->getStoreId());
- if ($method->acceptPayment($this)) {
- $invoice = $this->_getInvoiceForTransactionId($transactionId);
- $message = $this->_appendTransactionToMessage(
- $transactionId,
- $this->prependMessage(__('Approved the payment online.'))
- );
- $this->updateBaseAmountPaidOnlineTotal($invoice);
- $this->setOrderStateProcessing($message);
- } else {
- $message = $this->_appendTransactionToMessage(
- $transactionId,
- $this->prependMessage(__('There is no need to approve this payment.'))
- );
- $this->setOrderStatePaymentReview($message, $transactionId);
- }
- return $this;
- }
- /**
- * Accept order with payment method instance
- *
- * @param bool $isOnline
- * @return $this
- * @throws \Magento\Framework\Exception\LocalizedException
- */
- public function deny($isOnline = true)
- {
- $transactionId = $isOnline ? $this->getLastTransId() : $this->getTransactionId();
- if ($isOnline) {
- /** @var \Magento\Payment\Model\Method\AbstractMethod $method */
- $method = $this->getMethodInstance();
- $method->setStore($this->getOrder()->getStoreId());
- $result = $method->denyPayment($this);
- } else {
- $result = (bool)$this->getNotificationResult();
- }
- if ($result) {
- $invoice = $this->_getInvoiceForTransactionId($transactionId);
- $message = $this->_appendTransactionToMessage(
- $transactionId,
- $this->prependMessage(__('Denied the payment online'))
- );
- $this->cancelInvoiceAndRegisterCancellation($invoice, $message);
- } else {
- $txt = $isOnline ?
- 'There is no need to deny this payment.' : 'Registered notification about denied payment.';
- $message = $this->_appendTransactionToMessage(
- $transactionId,
- $this->prependMessage(__($txt))
- );
- $this->setOrderStatePaymentReview($message, $transactionId);
- }
- return $this;
- }
- /**
- * Performs registered payment update.
- *
- * @param bool $isOnline
- * @return $this
- * @throws \Magento\Framework\Exception\LocalizedException
- */
- public function update($isOnline = true)
- {
- $transactionId = $isOnline ? $this->getLastTransId() : $this->getTransactionId();
- $invoice = $this->_getInvoiceForTransactionId($transactionId);
- if ($isOnline) {
- $method = $this->getMethodInstance();
- $method->setStore($this->getOrder()->getStoreId());
- $method->fetchTransactionInfo($this, $transactionId);
- }
- if ($this->getIsTransactionApproved()) {
- $message = $this->_appendTransactionToMessage(
- $transactionId,
- $this->prependMessage(__('Registered update about approved payment.'))
- );
- $this->updateBaseAmountPaidOnlineTotal($invoice);
- $this->setOrderStateProcessing($message);
- } elseif ($this->getIsTransactionDenied()) {
- $message = $this->_appendTransactionToMessage(
- $transactionId,
- $this->prependMessage(__('Registered update about denied payment.'))
- );
- $this->cancelInvoiceAndRegisterCancellation($invoice, $message);
- } else {
- $message = $this->_appendTransactionToMessage(
- $transactionId,
- $this->prependMessage(__('There is no update for the payment.'))
- );
- $this->setOrderStatePaymentReview($message, $transactionId);
- }
- return $this;
- }
- /**
- * Triggers invoice pay and updates base_amount_paid_online total.
- *
- * @param \Magento\Sales\Model\Order\Invoice|false $invoice
- */
- protected function updateBaseAmountPaidOnlineTotal($invoice)
- {
- if ($invoice instanceof Invoice) {
- $invoice->pay();
- $totals = $this->collectTotalAmounts($this->getOrder(), ['base_grand_total']);
- $this->setBaseAmountPaidOnline($totals['base_grand_total']);
- $this->getOrder()->addRelatedObject($invoice);
- }
- }
- /**
- * Sets order state to 'processing' with appropriate message
- *
- * @param \Magento\Framework\Phrase|string $message
- */
- protected function setOrderStateProcessing($message)
- {
- $this->getOrder()->setState(Order::STATE_PROCESSING)
- ->setStatus($this->getOrder()->getConfig()->getStateDefaultStatus(Order::STATE_PROCESSING))
- ->addStatusHistoryComment($message);
- }
- /**
- * Cancel invoice and register order cancellation
- *
- * @param Invoice|false $invoice
- * @param string $message
- */
- protected function cancelInvoiceAndRegisterCancellation($invoice, $message)
- {
- if ($invoice instanceof Invoice) {
- $invoice->cancel();
- $this->getOrder()->addRelatedObject($invoice);
- }
- $this->getOrder()->registerCancellation($message, false);
- }
- /**
- * Sets order state status to 'payment_review' with appropriate message
- *
- * @param string $message
- * @param int|null $transactionId
- */
- protected function setOrderStatePaymentReview($message, $transactionId)
- {
- if ($this->getOrder()->getState() != Order::STATE_PAYMENT_REVIEW) {
- $this->getOrder()->setState(Order::STATE_PAYMENT_REVIEW)
- ->addStatusHistoryComment($message);
- if ($this->getIsFraudDetected()) {
- $this->getOrder()->setStatus(Order::STATUS_FRAUD);
- }
- if ($transactionId) {
- $this->setLastTransId($transactionId);
- }
- } else {
- $this->getOrder()->addStatusHistoryComment($message);
- }
- }
- /**
- * Triggers order payment command.
- *
- * This method can be used to support multi warehouse functionality
- * and notifies payment provider about the fact that order has been created.
- * 1. Updates order state and status to one of the following:
- * - processing, in case is_pending_payment flag is not set to a payment object
- * - payment_review, when is_pending_payment flag is set for payment object
- * - fraud, when is_fraud_detected flag is set to a payment object
- * 2. Sets corresponding comment for order and payment objects depending on order state value.
- * 3. Creates payment "order" transaction with corresponding comments
- *
- * For skipping 1,2,3 operations the skip_order_processing flag should be set in a payment object
- *
- * @param float $amount
- * @return $this
- */
- protected function _order($amount)
- {
- return $this->orderPaymentProcessor->order($this, $amount);
- }
- /**
- * Authorize payment either online or offline (process auth notification)
- * Updates transactions hierarchy, if required
- * Prevents transaction double processing
- * Updates payment totals, updates order status and adds proper comments
- *
- * @param bool $isOnline
- * @param float $amount
- *
- * @return $this
- */
- public function authorize($isOnline, $amount)
- {
- return $this->orderPaymentProcessor->authorize($this, $isOnline, $amount);
- }
- /**
- * Void payment either online or offline (process void notification)
- * NOTE: that in some cases authorization can be voided after a capture. In such case it makes sense to use
- * the amount void amount, for informational purposes.
- * Updates payment totals, updates order status and adds proper comments
- *
- * @param bool $isOnline
- * @param float $amount
- * @param string $gatewayCallback
- * @return $this
- * @SuppressWarnings(PHPMD.CyclomaticComplexity)
- * @SuppressWarnings(PHPMD.NPathComplexity)
- */
- protected function _void($isOnline, $amount = null, $gatewayCallback = 'void')
- {
- $order = $this->getOrder();
- $authTransaction = $this->getAuthorizationTransaction();
- $this->setTransactionId(
- $this->transactionManager->generateTransactionId($this, Transaction::TYPE_VOID, $authTransaction)
- );
- $this->setShouldCloseParentTransaction(true);
- // attempt to void
- if ($isOnline) {
- $method = $this->getMethodInstance();
- $method->setStore($order->getStoreId());
- $method->{$gatewayCallback}($this);
- }
- if ($this->checkIfTransactionExists()) {
- return $this;
- }
- // if the authorization was untouched, we may assume voided amount = order grand total
- // but only if the payment auth amount equals to order grand total
- if ($authTransaction &&
- $order->getBaseGrandTotal() == $this->getBaseAmountAuthorized() &&
- 0 == $this->getBaseAmountCanceled()
- ) {
- if ($authTransaction->canVoidAuthorizationCompletely()) {
- $amount = (double)$order->getBaseGrandTotal();
- }
- }
- if ($amount) {
- $amount = $this->formatAmount($amount);
- }
- // update transactions, order state and add comments
- $transaction = $this->addTransaction(Transaction::TYPE_VOID, null, true);
- $message = $this->hasMessage() ? $this->getMessage() : __('Voided authorization.');
- $message = $this->prependMessage($message);
- if ($amount) {
- $message .= ' ' . __('Amount: %1.', $this->formatPrice($amount));
- }
- $message = $this->_appendTransactionToMessage($transaction, $message);
- $this->setOrderStateProcessing($message);
- $order->setDataChanges(true);
- return $this;
- }
- /**
- * Public access to _addTransaction method
- *
- * @param string $type
- * @param \Magento\Sales\Model\AbstractModel $salesDocument
- * @param bool $failSafe
- * @return null|Transaction
- */
- public function addTransaction($type, $salesDocument = null, $failSafe = false)
- {
- $builder = $this->transactionBuilder->setPayment($this)
- ->setOrder($this->getOrder())
- ->setFailSafe($failSafe)
- ->setTransactionId($this->getTransactionId())
- ->setAdditionalInformation($this->transactionAdditionalInfo);
- if ($salesDocument) {
- $builder->setSalesDocument($salesDocument);
- }
- return $builder->build($type);
- }
- /**
- * Add message to the specified transaction.
- *
- * @param Transaction|null $transaction
- * @param string $message
- * @return void
- */
- public function addTransactionCommentsToOrder($transaction, $message)
- {
- $order = $this->getOrder();
- $message = $this->_appendTransactionToMessage($transaction, $message);
- $order->addStatusHistoryComment($message);
- }
- /**
- * Import details data of specified transaction
- *
- * @param Transaction $transactionTo
- * @return $this
- */
- public function importTransactionInfo(Transaction $transactionTo)
- {
- $method = $this->getMethodInstance();
- $method->setStore(
- $this->getOrder()->getStoreId()
- );
- $data = $method->fetchTransactionInfo(
- $this,
- $transactionTo->getTxnId()
- );
- if ($data) {
- $transactionTo->setAdditionalInformation(
- Transaction::RAW_DETAILS,
- $data
- );
- }
- return $this;
- }
- /**
- * Totals updater utility method
- *
- * Updates self totals by keys in data array('key' => $delta)
- *
- * @param array $data
- * @return void
- */
- protected function _updateTotals($data)
- {
- foreach ($data as $key => $amount) {
- if (null !== $amount) {
- $was = $this->getDataUsingMethod($key);
- $this->setDataUsingMethod($key, $was + $amount);
- }
- }
- }
- /**
- * Append transaction ID (if any) message to the specified message
- *
- * @param Transaction|null $transaction
- * @param string $message
- * @return string
- */
- protected function _appendTransactionToMessage($transaction, $message)
- {
- if ($transaction) {
- $txnId = is_object($transaction) ? $transaction->getHtmlTxnId() : $transaction;
- $message .= ' ' . __('Transaction ID: "%1"', $txnId);
- }
- return $message;
- }
- /**
- * Prepend a "prepared_message" that may be set to the payment instance before, to the specified message
- *
- * Prepends value to the specified string or to the comment of specified order status history item instance
- *
- * @param string|\Magento\Sales\Model\Order\Status\History $messagePrependTo
- * @return string|\Magento\Sales\Model\Order\Status\History
- */
- public function prependMessage($messagePrependTo)
- {
- $preparedMessage = $this->getPreparedMessage();
- if ($preparedMessage) {
- if (is_string($preparedMessage)
- || $preparedMessage instanceof \Magento\Framework\Phrase
- ) {
- return $preparedMessage . ' ' . $messagePrependTo;
- } elseif (is_object($preparedMessage)
- && $preparedMessage instanceof \Magento\Sales\Model\Order\Status\History
- ) {
- $comment = $preparedMessage->getComment() . ' ' . $messagePrependTo;
- $preparedMessage->setComment($comment);
- return $comment;
- }
- }
- return $messagePrependTo;
- }
- /**
- * Round up and cast specified amount to float or string
- *
- * @param string|float $amount
- * @param bool $asFloat
- * @return string|float
- */
- public function formatAmount($amount, $asFloat = false)
- {
- $amount = $this->priceCurrency->round($amount);
- return !$asFloat ? (string)$amount : $amount;
- }
- /**
- * Format price with currency sign
- *
- * @param float $amount
- * @return string
- */
- public function formatPrice($amount)
- {
- return $this->getOrder()->getBaseCurrency()->formatTxt($amount);
- }
- /**
- * Lookup an authorization transaction using parent transaction id, if set
- *
- * @return Transaction|false
- */
- public function getAuthorizationTransaction()
- {
- return $this->transactionManager->getAuthorizationTransaction(
- $this->getParentTransactionId(),
- $this->getId(),
- $this->getOrder()->getId()
- );
- }
- /**
- * Decide whether authorization transaction may close (if the amount to capture will cover entire order)
- *
- * @param float $amountToCapture
- * @return bool
- */
- public function isCaptureFinal($amountToCapture)
- {
- $total = $this->getOrder()->getBaseTotalDue();
- return $this->formatAmount($total, true) == $this->formatAmount($amountToCapture, true);
- }
- /**
- * Check whether payment currency corresponds to order currency
- *
- * @return bool
- */
- public function isSameCurrency()
- {
- return !$this->getCurrencyCode() || $this->getCurrencyCode() == $this->getOrder()->getBaseCurrencyCode();
- }
- /**
- * Additional transaction info setter
- *
- * @param string $key
- * @param string $value
- * @return void
- */
- public function setTransactionAdditionalInfo($key, $value)
- {
- $this->transactionAdditionalInfo[$key] = $value;
- }
- /**
- * Additional transaction info setter
- *
- * @return array
- */
- public function getTransactionAdditionalInfo()
- {
- return $this->transactionAdditionalInfo;
- }
- /**
- * Reset transaction additional info property
- *
- * @return $this
- */
- public function resetTransactionAdditionalInfo()
- {
- $this->transactionAdditionalInfo = [];
- return $this;
- }
- /**
- * Prepare credit memo
- *
- * @param float $amount
- * @param float $baseGrandTotal
- * @param false|Invoice $invoice
- * @return mixed
- */
- protected function prepareCreditMemo($amount, $baseGrandTotal, $invoice)
- {
- $entity = $invoice ?: $this->getOrder();
- if ($entity->getBaseTotalRefunded() > 0) {
- $adjustment = ['adjustment_positive' => $amount];
- } else {
- $adjustment = ['adjustment_negative' => $baseGrandTotal - $amount];
- }
- if ($invoice) {
- $creditMemo = $this->creditmemoFactory->createByInvoice($invoice, $adjustment);
- } else {
- $creditMemo = $this->creditmemoFactory->createByOrder($this->getOrder(), $adjustment);
- }
- if ($creditMemo) {
- $totalRefunded = $entity->getBaseTotalRefunded() + $creditMemo->getBaseGrandTotal();
- $this->setShouldCloseParentTransaction($entity->getBaseGrandTotal() <= $totalRefunded);
- }
- return $creditMemo;
- }
- /**
- * Checks if transaction exists
- *
- * @return bool
- */
- protected function checkIfTransactionExists()
- {
- return $this->transactionManager->isTransactionExists(
- $this->getTransactionId(),
- $this->getId(),
- $this->getOrder()->getId()
- );
- }
- /**
- * Return invoice model for transaction
- *
- * @param string $transactionId
- * @return Invoice|false
- */
- protected function _getInvoiceForTransactionId($transactionId)
- {
- foreach ($this->getOrder()->getInvoiceCollection() as $invoice) {
- if ($invoice->getTransactionId() == $transactionId) {
- $invoice->load($invoice->getId());
- // to make sure all data will properly load (maybe not required)
- return $invoice;
- }
- }
- foreach ($this->getOrder()->getInvoiceCollection() as $invoice) {
- if ($invoice->getState() == \Magento\Sales\Model\Order\Invoice::STATE_OPEN
- && $invoice->load($invoice->getId())
- ) {
- $invoice->setTransactionId($transactionId);
- return $invoice;
- }
- }
- return false;
- }
- /**
- * Get order state resolver instance.
- *
- * @deprecated 101.0.0
- * @return OrderStateResolverInterface
- */
- private function getOrderStateResolver()
- {
- if ($this->orderStateResolver === null) {
- $this->orderStateResolver = ObjectManager::getInstance()->get(OrderStateResolverInterface::class);
- }
- return $this->orderStateResolver;
- }
- //@codeCoverageIgnoreStart
- /**
- * Returns account_status
- *
- * @return string
- */
- public function getAccountStatus()
- {
- return $this->getData(OrderPaymentInterface::ACCOUNT_STATUS);
- }
- /**
- * Returns additional_data
- *
- * @return string
- */
- public function getAdditionalData()
- {
- return $this->getData(OrderPaymentInterface::ADDITIONAL_DATA);
- }
- /**
- * Returns address_status
- *
- * @return string
- */
- public function getAddressStatus()
- {
- return $this->getData(OrderPaymentInterface::ADDRESS_STATUS);
- }
- /**
- * Returns amount_authorized
- *
- * @return float
- */
- public function getAmountAuthorized()
- {
- return $this->getData(OrderPaymentInterface::AMOUNT_AUTHORIZED);
- }
- /**
- * Returns amount_canceled
- *
- * @return float
- */
- public function getAmountCanceled()
- {
- return $this->getData(OrderPaymentInterface::AMOUNT_CANCELED);
- }
- /**
- * Returns amount_ordered
- *
- * @return float
- */
- public function getAmountOrdered()
- {
- return $this->getData(OrderPaymentInterface::AMOUNT_ORDERED);
- }
- /**
- * Returns amount_paid
- *
- * @return float
- */
- public function getAmountPaid()
- {
- return $this->getData(OrderPaymentInterface::AMOUNT_PAID);
- }
- /**
- * Returns amount_refunded
- *
- * @return float
- */
- public function getAmountRefunded()
- {
- return $this->getData(OrderPaymentInterface::AMOUNT_REFUNDED);
- }
- /**
- * Returns anet_trans_method
- *
- * @return string
- */
- public function getAnetTransMethod()
- {
- return $this->getData(OrderPaymentInterface::ANET_TRANS_METHOD);
- }
- /**
- * Returns base_amount_authorized
- *
- * @return float
- */
- public function getBaseAmountAuthorized()
- {
- return $this->getData(OrderPaymentInterface::BASE_AMOUNT_AUTHORIZED);
- }
- /**
- * Returns base_amount_canceled
- *
- * @return float
- */
- public function getBaseAmountCanceled()
- {
- return $this->getData(OrderPaymentInterface::BASE_AMOUNT_CANCELED);
- }
- /**
- * Returns base_amount_ordered
- *
- * @return float
- */
- public function getBaseAmountOrdered()
- {
- return $this->getData(OrderPaymentInterface::BASE_AMOUNT_ORDERED);
- }
- /**
- * Returns base_amount_paid
- *
- * @return float
- */
- public function getBaseAmountPaid()
- {
- return $this->getData(OrderPaymentInterface::BASE_AMOUNT_PAID);
- }
- /**
- * Returns base_amount_paid_online
- *
- * @return float
- */
- public function getBaseAmountPaidOnline()
- {
- return $this->getData(OrderPaymentInterface::BASE_AMOUNT_PAID_ONLINE);
- }
- /**
- * Returns base_amount_refunded
- *
- * @return float
- */
- public function getBaseAmountRefunded()
- {
- return $this->getData(OrderPaymentInterface::BASE_AMOUNT_REFUNDED);
- }
- /**
- * Returns base_amount_refunded_online
- *
- * @return float
- */
- public function getBaseAmountRefundedOnline()
- {
- return $this->getData(OrderPaymentInterface::BASE_AMOUNT_REFUNDED_ONLINE);
- }
- /**
- * Returns base_shipping_amount
- *
- * @return float
- */
- public function getBaseShippingAmount()
- {
- return $this->getData(OrderPaymentInterface::BASE_SHIPPING_AMOUNT);
- }
- /**
- * Returns base_shipping_captured
- *
- * @return float
- */
- public function getBaseShippingCaptured()
- {
- return $this->getData(OrderPaymentInterface::BASE_SHIPPING_CAPTURED);
- }
- /**
- * Returns base_shipping_refunded
- *
- * @return float
- */
- public function getBaseShippingRefunded()
- {
- return $this->getData(OrderPaymentInterface::BASE_SHIPPING_REFUNDED);
- }
- /**
- * Returns cc_approval
- *
- * @return string
- */
- public function getCcApproval()
- {
- return $this->getData(OrderPaymentInterface::CC_APPROVAL);
- }
- /**
- * Returns cc_avs_status
- *
- * @return string
- */
- public function getCcAvsStatus()
- {
- return $this->getData(OrderPaymentInterface::CC_AVS_STATUS);
- }
- /**
- * Returns cc_cid_status
- *
- * @return string
- */
- public function getCcCidStatus()
- {
- return $this->getData(OrderPaymentInterface::CC_CID_STATUS);
- }
- /**
- * Returns cc_debug_request_body
- *
- * @return string
- */
- public function getCcDebugRequestBody()
- {
- return $this->getData(OrderPaymentInterface::CC_DEBUG_REQUEST_BODY);
- }
- /**
- * Returns cc_debug_response_body
- *
- * @return string
- */
- public function getCcDebugResponseBody()
- {
- return $this->getData(OrderPaymentInterface::CC_DEBUG_RESPONSE_BODY);
- }
- /**
- * Returns cc_debug_response_serialized
- *
- * @return string
- */
- public function getCcDebugResponseSerialized()
- {
- return $this->getData(OrderPaymentInterface::CC_DEBUG_RESPONSE_SERIALIZED);
- }
- /**
- * Returns cc_exp_month
- *
- * @return string
- */
- public function getCcExpMonth()
- {
- return $this->getData(OrderPaymentInterface::CC_EXP_MONTH);
- }
- /**
- * Returns cc_exp_year
- *
- * @return string
- */
- public function getCcExpYear()
- {
- return $this->getData(OrderPaymentInterface::CC_EXP_YEAR);
- }
- /**
- * Returns cc_last_4
- *
- * @return string
- */
- public function getCcLast4()
- {
- return $this->getData(OrderPaymentInterface::CC_LAST_4);
- }
- /**
- * Returns cc_number_enc
- *
- * @return string
- */
- public function getCcNumberEnc()
- {
- return $this->getData(OrderPaymentInterface::CC_NUMBER_ENC);
- }
- /**
- * Returns cc_owner
- *
- * @return string
- */
- public function getCcOwner()
- {
- return $this->getData(OrderPaymentInterface::CC_OWNER);
- }
- /**
- * Returns cc_secure_verify
- *
- * @return string
- */
- public function getCcSecureVerify()
- {
- return $this->getData(OrderPaymentInterface::CC_SECURE_VERIFY);
- }
- /**
- * Returns cc_ss_issue
- *
- * @return string
- * @deprecated 100.1.0 unused
- */
- public function getCcSsIssue()
- {
- return $this->getData(OrderPaymentInterface::CC_SS_ISSUE);
- }
- /**
- * Returns cc_ss_start_month
- *
- * @return string
- * @deprecated 100.1.0 unused
- */
- public function getCcSsStartMonth()
- {
- return $this->getData(OrderPaymentInterface::CC_SS_START_MONTH);
- }
- /**
- * Returns cc_ss_start_year
- *
- * @return string
- * @deprecated 100.1.0 unused
- */
- public function getCcSsStartYear()
- {
- return $this->getData(OrderPaymentInterface::CC_SS_START_YEAR);
- }
- /**
- * Returns cc_status
- *
- * @return string
- */
- public function getCcStatus()
- {
- return $this->getData(OrderPaymentInterface::CC_STATUS);
- }
- /**
- * Returns cc_status_description
- *
- * @return string
- */
- public function getCcStatusDescription()
- {
- return $this->getData(OrderPaymentInterface::CC_STATUS_DESCRIPTION);
- }
- /**
- * Returns cc_trans_id
- *
- * @return string
- */
- public function getCcTransId()
- {
- return $this->getData(OrderPaymentInterface::CC_TRANS_ID);
- }
- /**
- * Returns cc_type
- *
- * @return string
- */
- public function getCcType()
- {
- return $this->getData(OrderPaymentInterface::CC_TYPE);
- }
- /**
- * Returns echeck_account_name
- *
- * @return string
- */
- public function getEcheckAccountName()
- {
- return $this->getData(OrderPaymentInterface::ECHECK_ACCOUNT_NAME);
- }
- /**
- * Returns echeck_account_type
- *
- * @return string
- */
- public function getEcheckAccountType()
- {
- return $this->getData(OrderPaymentInterface::ECHECK_ACCOUNT_TYPE);
- }
- /**
- * Returns echeck_bank_name
- *
- * @return string
- */
- public function getEcheckBankName()
- {
- return $this->getData(OrderPaymentInterface::ECHECK_BANK_NAME);
- }
- /**
- * Returns echeck_routing_number
- *
- * @return string
- */
- public function getEcheckRoutingNumber()
- {
- return $this->getData(OrderPaymentInterface::ECHECK_ROUTING_NUMBER);
- }
- /**
- * Returns echeck_type
- *
- * @return string
- */
- public function getEcheckType()
- {
- return $this->getData(OrderPaymentInterface::ECHECK_TYPE);
- }
- /**
- * Returns last_trans_id
- *
- * @return string
- */
- public function getLastTransId()
- {
- return $this->getData(OrderPaymentInterface::LAST_TRANS_ID);
- }
- /**
- * Returns method
- *
- * @return string
- */
- public function getMethod()
- {
- return $this->getData(OrderPaymentInterface::METHOD);
- }
- /**
- * Returns parent_id
- *
- * @return int
- */
- public function getParentId()
- {
- return $this->getData(OrderPaymentInterface::PARENT_ID);
- }
- /**
- * Returns po_number
- *
- * @return string
- */
- public function getPoNumber()
- {
- return $this->getData(OrderPaymentInterface::PO_NUMBER);
- }
- /**
- * Returns protection_eligibility
- *
- * @return string
- */
- public function getProtectionEligibility()
- {
- return $this->getData(OrderPaymentInterface::PROTECTION_ELIGIBILITY);
- }
- /**
- * Returns quote_payment_id
- *
- * @return int
- */
- public function getQuotePaymentId()
- {
- return $this->getData(OrderPaymentInterface::QUOTE_PAYMENT_ID);
- }
- /**
- * Returns shipping_amount
- *
- * @return float
- */
- public function getShippingAmount()
- {
- return $this->getData(OrderPaymentInterface::SHIPPING_AMOUNT);
- }
- /**
- * Returns shipping_captured
- *
- * @return float
- */
- public function getShippingCaptured()
- {
- return $this->getData(OrderPaymentInterface::SHIPPING_CAPTURED);
- }
- /**
- * Returns shipping_refunded
- *
- * @return float
- */
- public function getShippingRefunded()
- {
- return $this->getData(OrderPaymentInterface::SHIPPING_REFUNDED);
- }
- /**
- * @inheritdoc
- */
- public function setParentId($id)
- {
- return $this->setData(OrderPaymentInterface::PARENT_ID, $id);
- }
- /**
- * @inheritdoc
- */
- public function setBaseShippingCaptured($baseShippingCaptured)
- {
- return $this->setData(OrderPaymentInterface::BASE_SHIPPING_CAPTURED, $baseShippingCaptured);
- }
- /**
- * @inheritdoc
- */
- public function setShippingCaptured($shippingCaptured)
- {
- return $this->setData(OrderPaymentInterface::SHIPPING_CAPTURED, $shippingCaptured);
- }
- /**
- * @inheritdoc
- */
- public function setAmountRefunded($amountRefunded)
- {
- return $this->setData(OrderPaymentInterface::AMOUNT_REFUNDED, $amountRefunded);
- }
- /**
- * @inheritdoc
- */
- public function setBaseAmountPaid($baseAmountPaid)
- {
- return $this->setData(OrderPaymentInterface::BASE_AMOUNT_PAID, $baseAmountPaid);
- }
- /**
- * @inheritdoc
- */
- public function setAmountCanceled($amountCanceled)
- {
- return $this->setData(OrderPaymentInterface::AMOUNT_CANCELED, $amountCanceled);
- }
- /**
- * @inheritdoc
- */
- public function setBaseAmountAuthorized($baseAmountAuthorized)
- {
- return $this->setData(OrderPaymentInterface::BASE_AMOUNT_AUTHORIZED, $baseAmountAuthorized);
- }
- /**
- * @inheritdoc
- */
- public function setBaseAmountPaidOnline($baseAmountPaidOnline)
- {
- return $this->setData(OrderPaymentInterface::BASE_AMOUNT_PAID_ONLINE, $baseAmountPaidOnline);
- }
- /**
- * @inheritdoc
- */
- public function setBaseAmountRefundedOnline($baseAmountRefundedOnline)
- {
- return $this->setData(OrderPaymentInterface::BASE_AMOUNT_REFUNDED_ONLINE, $baseAmountRefundedOnline);
- }
- /**
- * @inheritdoc
- */
- public function setBaseShippingAmount($amount)
- {
- return $this->setData(OrderPaymentInterface::BASE_SHIPPING_AMOUNT, $amount);
- }
- /**
- * @inheritdoc
- */
- public function setShippingAmount($amount)
- {
- return $this->setData(OrderPaymentInterface::SHIPPING_AMOUNT, $amount);
- }
- /**
- * @inheritdoc
- */
- public function setAmountPaid($amountPaid)
- {
- return $this->setData(OrderPaymentInterface::AMOUNT_PAID, $amountPaid);
- }
- /**
- * @inheritdoc
- */
- public function setAmountAuthorized($amountAuthorized)
- {
- return $this->setData(OrderPaymentInterface::AMOUNT_AUTHORIZED, $amountAuthorized);
- }
- /**
- * @inheritdoc
- */
- public function setBaseAmountOrdered($baseAmountOrdered)
- {
- return $this->setData(OrderPaymentInterface::BASE_AMOUNT_ORDERED, $baseAmountOrdered);
- }
- /**
- * @inheritdoc
- */
- public function setBaseShippingRefunded($baseShippingRefunded)
- {
- return $this->setData(OrderPaymentInterface::BASE_SHIPPING_REFUNDED, $baseShippingRefunded);
- }
- /**
- * @inheritdoc
- */
- public function setShippingRefunded($shippingRefunded)
- {
- return $this->setData(OrderPaymentInterface::SHIPPING_REFUNDED, $shippingRefunded);
- }
- /**
- * @inheritdoc
- */
- public function setBaseAmountRefunded($baseAmountRefunded)
- {
- return $this->setData(OrderPaymentInterface::BASE_AMOUNT_REFUNDED, $baseAmountRefunded);
- }
- /**
- * @inheritdoc
- */
- public function setAmountOrdered($amountOrdered)
- {
- return $this->setData(OrderPaymentInterface::AMOUNT_ORDERED, $amountOrdered);
- }
- /**
- * @inheritdoc
- */
- public function setBaseAmountCanceled($baseAmountCanceled)
- {
- return $this->setData(OrderPaymentInterface::BASE_AMOUNT_CANCELED, $baseAmountCanceled);
- }
- /**
- * @inheritdoc
- */
- public function setQuotePaymentId($id)
- {
- return $this->setData(OrderPaymentInterface::QUOTE_PAYMENT_ID, $id);
- }
- /**
- * @inheritdoc
- */
- public function setAdditionalData($additionalData)
- {
- return $this->setData(OrderPaymentInterface::ADDITIONAL_DATA, $additionalData);
- }
- /**
- * @inheritdoc
- */
- public function setCcExpMonth($ccExpMonth)
- {
- return $this->setData(OrderPaymentInterface::CC_EXP_MONTH, $ccExpMonth);
- }
- /**
- * @inheritdoc
- * @deprecated 100.1.0 unused
- */
- public function setCcSsStartYear($ccSsStartYear)
- {
- return $this->setData(OrderPaymentInterface::CC_SS_START_YEAR, $ccSsStartYear);
- }
- /**
- * @inheritdoc
- */
- public function setEcheckBankName($echeckBankName)
- {
- return $this->setData(OrderPaymentInterface::ECHECK_BANK_NAME, $echeckBankName);
- }
- /**
- * @inheritdoc
- */
- public function setMethod($method)
- {
- return $this->setData(OrderPaymentInterface::METHOD, $method);
- }
- /**
- * @inheritdoc
- */
- public function setCcDebugRequestBody($ccDebugRequestBody)
- {
- return $this->setData(OrderPaymentInterface::CC_DEBUG_REQUEST_BODY, $ccDebugRequestBody);
- }
- /**
- * @inheritdoc
- */
- public function setCcSecureVerify($ccSecureVerify)
- {
- return $this->setData(OrderPaymentInterface::CC_SECURE_VERIFY, $ccSecureVerify);
- }
- /**
- * @inheritdoc
- */
- public function setProtectionEligibility($protectionEligibility)
- {
- return $this->setData(OrderPaymentInterface::PROTECTION_ELIGIBILITY, $protectionEligibility);
- }
- /**
- * @inheritdoc
- */
- public function setCcApproval($ccApproval)
- {
- return $this->setData(OrderPaymentInterface::CC_APPROVAL, $ccApproval);
- }
- /**
- * @inheritdoc
- */
- public function setCcLast4($ccLast4)
- {
- return $this->setData(OrderPaymentInterface::CC_LAST_4, $ccLast4);
- }
- /**
- * @inheritdoc
- */
- public function setCcStatusDescription($description)
- {
- return $this->setData(OrderPaymentInterface::CC_STATUS_DESCRIPTION, $description);
- }
- /**
- * @inheritdoc
- */
- public function setEcheckType($echeckType)
- {
- return $this->setData(OrderPaymentInterface::ECHECK_TYPE, $echeckType);
- }
- /**
- * @inheritdoc
- */
- public function setCcDebugResponseSerialized($ccDebugResponseSerialized)
- {
- return $this->setData(OrderPaymentInterface::CC_DEBUG_RESPONSE_SERIALIZED, $ccDebugResponseSerialized);
- }
- /**
- * @inheritdoc
- * @deprecated 100.1.0 unused
- */
- public function setCcSsStartMonth($ccSsStartMonth)
- {
- return $this->setData(OrderPaymentInterface::CC_SS_START_MONTH, $ccSsStartMonth);
- }
- /**
- * @inheritdoc
- */
- public function setEcheckAccountType($echeckAccountType)
- {
- return $this->setData(OrderPaymentInterface::ECHECK_ACCOUNT_TYPE, $echeckAccountType);
- }
- /**
- * @inheritdoc
- */
- public function setLastTransId($id)
- {
- return $this->setData(OrderPaymentInterface::LAST_TRANS_ID, $id);
- }
- /**
- * @inheritdoc
- */
- public function setCcCidStatus($ccCidStatus)
- {
- return $this->setData(OrderPaymentInterface::CC_CID_STATUS, $ccCidStatus);
- }
- /**
- * @inheritdoc
- */
- public function setCcOwner($ccOwner)
- {
- return $this->setData(OrderPaymentInterface::CC_OWNER, $ccOwner);
- }
- /**
- * @inheritdoc
- */
- public function setCcType($ccType)
- {
- return $this->setData(OrderPaymentInterface::CC_TYPE, $ccType);
- }
- /**
- * @inheritdoc
- */
- public function setPoNumber($poNumber)
- {
- return $this->setData(OrderPaymentInterface::PO_NUMBER, $poNumber);
- }
- /**
- * @inheritdoc
- */
- public function setCcExpYear($ccExpYear)
- {
- return $this->setData(OrderPaymentInterface::CC_EXP_YEAR, $ccExpYear);
- }
- /**
- * @inheritdoc
- */
- public function setCcStatus($ccStatus)
- {
- return $this->setData(OrderPaymentInterface::CC_STATUS, $ccStatus);
- }
- /**
- * @inheritdoc
- */
- public function setEcheckRoutingNumber($echeckRoutingNumber)
- {
- return $this->setData(OrderPaymentInterface::ECHECK_ROUTING_NUMBER, $echeckRoutingNumber);
- }
- /**
- * @inheritdoc
- */
- public function setAccountStatus($accountStatus)
- {
- return $this->setData(OrderPaymentInterface::ACCOUNT_STATUS, $accountStatus);
- }
- /**
- * @inheritdoc
- */
- public function setAnetTransMethod($anetTransMethod)
- {
- return $this->setData(OrderPaymentInterface::ANET_TRANS_METHOD, $anetTransMethod);
- }
- /**
- * @inheritdoc
- */
- public function setCcDebugResponseBody($ccDebugResponseBody)
- {
- return $this->setData(OrderPaymentInterface::CC_DEBUG_RESPONSE_BODY, $ccDebugResponseBody);
- }
- /**
- * @inheritdoc
- * @deprecated 100.1.0 unused
- */
- public function setCcSsIssue($ccSsIssue)
- {
- return $this->setData(OrderPaymentInterface::CC_SS_ISSUE, $ccSsIssue);
- }
- /**
- * @inheritdoc
- */
- public function setEcheckAccountName($echeckAccountName)
- {
- return $this->setData(OrderPaymentInterface::ECHECK_ACCOUNT_NAME, $echeckAccountName);
- }
- /**
- * @inheritdoc
- */
- public function setCcAvsStatus($ccAvsStatus)
- {
- return $this->setData(OrderPaymentInterface::CC_AVS_STATUS, $ccAvsStatus);
- }
- /**
- * @inheritdoc
- */
- public function setCcNumberEnc($ccNumberEnc)
- {
- return $this->setData(OrderPaymentInterface::CC_NUMBER_ENC, $ccNumberEnc);
- }
- /**
- * @inheritdoc
- */
- public function setCcTransId($id)
- {
- return $this->setData(OrderPaymentInterface::CC_TRANS_ID, $id);
- }
- /**
- * @inheritdoc
- */
- public function setAddressStatus($addressStatus)
- {
- return $this->setData(OrderPaymentInterface::ADDRESS_STATUS, $addressStatus);
- }
- /**
- * @inheritdoc
- *
- * @return \Magento\Sales\Api\Data\OrderPaymentExtensionInterface|null
- */
- public function getExtensionAttributes()
- {
- return $this->_getExtensionAttributes();
- }
- /**
- * @inheritdoc
- *
- * @param \Magento\Sales\Api\Data\OrderPaymentExtensionInterface $extensionAttributes
- * @return $this
- */
- public function setExtensionAttributes(\Magento\Sales\Api\Data\OrderPaymentExtensionInterface $extensionAttributes)
- {
- return $this->_setExtensionAttributes($extensionAttributes);
- }
- /**
- * Sets whether transaction is pending
- *
- * @param bool|int $flag
- * @return $this
- */
- public function setIsTransactionPending($flag)
- {
- $this->setData('is_transaction_pending', (bool)$flag);
- return $this;
- }
- /**
- * Whether transaction is pending
- *
- * @return bool
- * @SuppressWarnings(PHPMD.BooleanGetMethodName)
- */
- public function getIsTransactionPending()
- {
- return (bool)$this->getData('is_transaction_pending');
- }
- /**
- * Sets whether fraud was detected
- *
- * @param bool|int $flag
- * @return $this
- */
- public function setIsFraudDetected($flag)
- {
- $this->setData('is_fraud_detected', (bool)$flag);
- return $this;
- }
- /**
- * Whether fraud was detected
- *
- * @return bool
- * @SuppressWarnings(PHPMD.BooleanGetMethodName)
- */
- public function getIsFraudDetected()
- {
- return (bool)$this->getData('is_fraud_detected');
- }
- /**
- * Sets whether should close parent transaction
- *
- * @param int|bool $flag
- * @return $this
- */
- public function setShouldCloseParentTransaction($flag)
- {
- $this->setData('should_close_parent_transaction', (bool)$flag);
- return $this;
- }
- /**
- * Whether should close parent transaction
- *
- * @return bool
- * @SuppressWarnings(PHPMD.BooleanGetMethodName)
- */
- public function getShouldCloseParentTransaction()
- {
- return (bool)$this->getData('should_close_parent_transaction');
- }
- /**
- * Set payment parent transaction id and current transaction id if it not set
- *
- * @param Transaction $transaction
- * @return void
- */
- private function setTransactionIdsForRefund(Transaction $transaction)
- {
- if (!$this->getTransactionId()) {
- $this->setTransactionId(
- $this->transactionManager->generateTransactionId(
- $this,
- Transaction::TYPE_REFUND,
- $transaction
- )
- );
- }
- $this->setParentTransactionId($transaction->getTxnId());
- }
- //@codeCoverageIgnoreEnd
- /**
- * Collects order invoices totals by provided keys.
- *
- * Returns result as {key: amount}.
- *
- * @param Order $order
- * @param array $keys
- * @return array
- */
- private function collectTotalAmounts(Order $order, array $keys)
- {
- $result = array_fill_keys($keys, 0.00);
- $invoiceCollection = $order->getInvoiceCollection();
- /** @var Invoice $invoice */
- foreach ($invoiceCollection as $invoice) {
- foreach ($keys as $key) {
- $result[$key] += $invoice->getData($key);
- }
- }
- return $result;
- }
- }
|