PageRenderTime 156ms CodeModel.GetById 81ms app.highlight 18ms RepoModel.GetById 52ms app.codeStats 1ms

/app/code/core/Mage/Adminhtml/controllers/Sales/Order/InvoiceController.php

https://bitbucket.org/claudiu_marginean/magento-hg-mirror
PHP | 481 lines | 330 code | 44 blank | 107 comment | 51 complexity | ac306e143b3a9e136720a525b5b05d23 MD5 | raw file
  1<?php
  2/**
  3 * Magento
  4 *
  5 * NOTICE OF LICENSE
  6 *
  7 * This source file is subject to the Open Software License (OSL 3.0)
  8 * that is bundled with this package in the file LICENSE.txt.
  9 * It is also available through the world-wide-web at this URL:
 10 * http://opensource.org/licenses/osl-3.0.php
 11 * If you did not receive a copy of the license and are unable to
 12 * obtain it through the world-wide-web, please send an email
 13 * to license@magentocommerce.com so we can send you a copy immediately.
 14 *
 15 * DISCLAIMER
 16 *
 17 * Do not edit or add to this file if you wish to upgrade Magento to newer
 18 * versions in the future. If you wish to customize Magento for your
 19 * needs please refer to http://www.magentocommerce.com for more information.
 20 *
 21 * @category    Mage
 22 * @package     Mage_Adminhtml
 23 * @copyright   Copyright (c) 2010 Magento Inc. (http://www.magentocommerce.com)
 24 * @license     http://opensource.org/licenses/osl-3.0.php  Open Software License (OSL 3.0)
 25 */
 26
 27/**
 28 * Adminhtml sales order edit controller
 29 *
 30 * @category   Mage
 31 * @package    Mage_Adminhtml
 32 * @author      Magento Core Team <core@magentocommerce.com>
 33 */
 34class Mage_Adminhtml_Sales_Order_InvoiceController extends Mage_Adminhtml_Controller_Sales_Invoice
 35{
 36    /**
 37     * Get requested items qty's from request
 38     */
 39    protected function _getItemQtys()
 40    {
 41        $data = $this->getRequest()->getParam('invoice');
 42        if (isset($data['items'])) {
 43            $qtys = $data['items'];
 44        } else {
 45            $qtys = array();
 46        }
 47        return $qtys;
 48    }
 49
 50    /**
 51     * Initialize invoice model instance
 52     *
 53     * @return Mage_Sales_Model_Order_Invoice
 54     */
 55    protected function _initInvoice($update = false)
 56    {
 57        $this->_title($this->__('Sales'))->_title($this->__('Invoices'));
 58
 59        $invoice = false;
 60        $itemsToInvoice = 0;
 61        $invoiceId = $this->getRequest()->getParam('invoice_id');
 62        $orderId = $this->getRequest()->getParam('order_id');
 63        if ($invoiceId) {
 64            $invoice = Mage::getModel('sales/order_invoice')->load($invoiceId);
 65            if (!$invoice->getId()) {
 66                $this->_getSession()->addError($this->__('The invoice no longer exists.'));
 67                return false;
 68            }
 69        } elseif ($orderId) {
 70            $order = Mage::getModel('sales/order')->load($orderId);
 71            /**
 72             * Check order existing
 73             */
 74            if (!$order->getId()) {
 75                $this->_getSession()->addError($this->__('The order no longer exists.'));
 76                return false;
 77            }
 78            /**
 79             * Check invoice create availability
 80             */
 81            if (!$order->canInvoice()) {
 82                $this->_getSession()->addError($this->__('The order does not allow creating an invoice.'));
 83                return false;
 84            }
 85            $savedQtys = $this->_getItemQtys();
 86            $invoice = Mage::getModel('sales/service_order', $order)->prepareInvoice($savedQtys);
 87            if (!$invoice->getTotalQty()) {
 88                Mage::throwException($this->__('Cannot create an invoice without products.'));
 89            }
 90        }
 91
 92        Mage::register('current_invoice', $invoice);
 93        return $invoice;
 94    }
 95
 96    /**
 97     * Save data for invoice and related order
 98     *
 99     * @param   Mage_Sales_Model_Order_Invoice $invoice
100     * @return  Mage_Adminhtml_Sales_Order_InvoiceController
101     */
102    protected function _saveInvoice($invoice)
103    {
104        $invoice->getOrder()->setIsInProcess(true);
105        $transactionSave = Mage::getModel('core/resource_transaction')
106            ->addObject($invoice)
107            ->addObject($invoice->getOrder())
108            ->save();
109
110        return $this;
111    }
112
113    /**
114     * Prepare shipment
115     *
116     * @param Mage_Sales_Model_Order_Invoice $invoice
117     * @return Mage_Sales_Model_Order_Shipment
118     */
119    protected function _prepareShipment($invoice)
120    {
121        $savedQtys = $this->_getItemQtys();
122        $shipment = Mage::getModel('sales/service_order', $invoice->getOrder())->prepareShipment($savedQtys);
123        if (!$shipment->getTotalQty()) {
124            return false;
125        }
126
127
128        $shipment->register();
129        $tracks = $this->getRequest()->getPost('tracking');
130        if ($tracks) {
131            foreach ($tracks as $data) {
132                $track = Mage::getModel('sales/order_shipment_track')
133                    ->addData($data);
134                $shipment->addTrack($track);
135            }
136        }
137        return $shipment;
138    }
139
140    /**
141     * Invoice information page
142     */
143    public function viewAction()
144    {
145        $invoice = $this->_initInvoice();
146        if ($invoice) {
147            $this->_title(sprintf("#%s", $invoice->getIncrementId()));
148
149            $this->loadLayout()
150                ->_setActiveMenu('sales/order');
151            $this->getLayout()->getBlock('sales_invoice_view')
152                ->updateBackButtonUrl($this->getRequest()->getParam('come_from'));
153            $this->renderLayout();
154        }
155        else {
156            $this->_forward('noRoute');
157        }
158    }
159
160    /**
161     * Start create invoice action
162     */
163    public function startAction()
164    {
165        /**
166         * Clear old values for invoice qty's
167         */
168        $this->_getSession()->getInvoiceItemQtys(true);
169        $this->_redirect('*/*/new', array('order_id'=>$this->getRequest()->getParam('order_id')));
170    }
171
172    /**
173     * Invoice create page
174     */
175    public function newAction()
176    {
177        $invoice = $this->_initInvoice();
178        if ($invoice) {
179            $this->_title($this->__('New Invoice'));
180
181            if ($comment = Mage::getSingleton('adminhtml/session')->getCommentText(true)) {
182                $invoice->setCommentText($comment);
183            }
184
185            $this->loadLayout()
186                ->_setActiveMenu('sales/order')
187                ->renderLayout();
188        } else {
189            $this->_redirect('*/sales_order/view', array('order_id'=>$this->getRequest()->getParam('order_id')));
190        }
191    }
192
193    /**
194     * Update items qty action
195     */
196    public function updateQtyAction()
197    {
198        try {
199            $invoice = $this->_initInvoice(true);
200            // Save invoice comment text in current invoice object in order to display it in corresponding view
201            $invoiceRawData = $this->getRequest()->getParam('invoice');
202            $invoiceRawCommentText = $invoiceRawData['comment_text'];
203            $invoice->setCommentText($invoiceRawCommentText);
204
205            $this->loadLayout();
206            $response = $this->getLayout()->getBlock('order_items')->toHtml();
207        } catch (Mage_Core_Exception $e) {
208            $response = array(
209                'error'     => true,
210                'message'   => $e->getMessage()
211            );
212            $response = Mage::helper('core')->jsonEncode($response);
213        } catch (Exception $e) {
214            $response = array(
215                'error'     => true,
216                'message'   => $this->__('Cannot update item quantity.')
217            );
218            $response = Mage::helper('core')->jsonEncode($response);
219        }
220        $this->getResponse()->setBody($response);
221    }
222
223    /**
224     * Save invoice
225     * We can save only new invoice. Existing invoices are not editable
226     */
227    public function saveAction()
228    {
229        $data = $this->getRequest()->getPost('invoice');
230        $orderId = $this->getRequest()->getParam('order_id');
231
232        if (!empty($data['comment_text'])) {
233            Mage::getSingleton('adminhtml/session')->setCommentText($data['comment_text']);
234        }
235
236        try {
237            $invoice = $this->_initInvoice();
238            if ($invoice) {
239
240                if (!empty($data['capture_case'])) {
241                    $invoice->setRequestedCaptureCase($data['capture_case']);
242                }
243
244                if (!empty($data['comment_text'])) {
245                    $invoice->addComment(
246                        $data['comment_text'],
247                        isset($data['comment_customer_notify']),
248                        isset($data['is_visible_on_front'])
249                    );
250                }
251
252                $invoice->register();
253
254                if (!empty($data['send_email'])) {
255                    $invoice->setEmailSent(true);
256                }
257
258                $invoice->getOrder()->setCustomerNoteNotify(!empty($data['send_email']));
259                $invoice->getOrder()->setIsInProcess(true);
260
261                $transactionSave = Mage::getModel('core/resource_transaction')
262                    ->addObject($invoice)
263                    ->addObject($invoice->getOrder());
264                $shipment = false;
265                if (!empty($data['do_shipment']) || (int) $invoice->getOrder()->getForcedDoShipmentWithInvoice()) {
266                    $shipment = $this->_prepareShipment($invoice);
267                    if ($shipment) {
268                        $shipment->setEmailSent($invoice->getEmailSent());
269                        $transactionSave->addObject($shipment);
270                    }
271                }
272                $transactionSave->save();
273
274                if (!empty($data['do_shipment'])) {
275                    $this->_getSession()->addSuccess($this->__('The invoice and shipment have been created.'));
276                } else {
277                    $this->_getSession()->addSuccess($this->__('The invoice has been created.'));
278                }
279
280                // send invoice/shipment emails
281                $comment = '';
282                if (isset($data['comment_customer_notify'])) {
283                    $comment = $data['comment_text'];
284                }
285                try {
286                    $invoice->sendEmail(!empty($data['send_email']), $comment);
287                } catch (Exception $e) {
288                    Mage::logException($e);
289                    $this->_getSession()->addError($this->__('Unable to send the invoice email.'));
290                }
291                if ($shipment) {
292                    try {
293                        $shipment->sendEmail(!empty($data['send_email']));
294                    } catch (Exception $e) {
295                        Mage::logException($e);
296                        $this->_getSession()->addError($this->__('Unable to send the shipment email.'));
297                    }
298                }
299                Mage::getSingleton('adminhtml/session')->getCommentText(true);
300                $this->_redirect('*/sales_order/view', array('order_id' => $orderId));
301            } else {
302                $this->_redirect('*/*/new', array('order_id' => $orderId));
303            }
304            return;
305        } catch (Mage_Core_Exception $e) {
306            $this->_getSession()->addError($e->getMessage());
307        } catch (Exception $e) {
308            $this->_getSession()->addError($this->__('Unable to save the invoice.'));
309            Mage::logException($e);
310        }
311        $this->_redirect('*/*/new', array('order_id' => $orderId));
312    }
313
314
315    /**
316     * Capture invoice action
317     */
318    public function captureAction()
319    {
320        if ($invoice = $this->_initInvoice()) {
321            try {
322                $invoice->capture();
323                $this->_saveInvoice($invoice);
324                $this->_getSession()->addSuccess($this->__('The invoice has been captured.'));
325            } catch (Mage_Core_Exception $e) {
326                $this->_getSession()->addError($e->getMessage());
327            } catch (Exception $e) {
328                $this->_getSession()->addError($this->__('Invoice capturing error.'));
329            }
330            $this->_redirect('*/*/view', array('invoice_id'=>$invoice->getId()));
331        } else {
332            $this->_forward('noRoute');
333        }
334    }
335
336    /**
337     * Cancel invoice action
338     */
339    public function cancelAction()
340    {
341        if ($invoice = $this->_initInvoice()) {
342            try {
343                $invoice->cancel();
344                $this->_saveInvoice($invoice);
345                $this->_getSession()->addSuccess($this->__('The invoice has been canceled.'));
346            } catch (Mage_Core_Exception $e) {
347                $this->_getSession()->addError($e->getMessage());
348            } catch (Exception $e) {
349                $this->_getSession()->addError($this->__('Invoice canceling error.'));
350            }
351            $this->_redirect('*/*/view', array('invoice_id'=>$invoice->getId()));
352        } else {
353            $this->_forward('noRoute');
354        }
355    }
356
357    /**
358     * Void invoice action
359     */
360    public function voidAction()
361    {
362        if ($invoice = $this->_initInvoice()) {
363            try {
364                $invoice->void();
365                $this->_saveInvoice($invoice);
366                $this->_getSession()->addSuccess($this->__('The invoice has been voided.'));
367            } catch (Mage_Core_Exception $e) {
368                $this->_getSession()->addError($e->getMessage());
369            } catch (Exception $e) {
370                $this->_getSession()->addError($this->__('Invoice voiding error.'));
371            }
372            $this->_redirect('*/*/view', array('invoice_id'=>$invoice->getId()));
373        } else {
374            $this->_forward('noRoute');
375        }
376    }
377
378    public function addCommentAction()
379    {
380        try {
381            $this->getRequest()->setParam('invoice_id', $this->getRequest()->getParam('id'));
382            $data = $this->getRequest()->getPost('comment');
383            if (empty($data['comment'])) {
384                Mage::throwException($this->__('The Comment Text field cannot be empty.'));
385            }
386            $invoice = $this->_initInvoice();
387            $invoice->addComment(
388                $data['comment'],
389                isset($data['is_customer_notified']),
390                isset($data['is_visible_on_front'])
391            );
392            $invoice->sendUpdateEmail(!empty($data['is_customer_notified']), $data['comment']);
393            $invoice->save();
394
395            $this->loadLayout();
396            $response = $this->getLayout()->getBlock('invoice_comments')->toHtml();
397        } catch (Mage_Core_Exception $e) {
398            $response = array(
399                'error'     => true,
400                'message'   => $e->getMessage()
401            );
402            $response = Mage::helper('core')->jsonEncode($response);
403        } catch (Exception $e) {
404            $response = array(
405                'error'     => true,
406                'message'   => $this->__('Cannot add new comment.')
407            );
408            $response = Mage::helper('core')->jsonEncode($response);
409        }
410        $this->getResponse()->setBody($response);
411    }
412
413
414
415
416
417
418
419
420    /**
421     * Decides if we need to create dummy invoice item or not
422     * for eaxample we don't need create dummy parent if all
423     * children are not in process
424     *
425     * @deprecated after 1.4, Mage_Sales_Model_Service_Order used
426     * @param Mage_Sales_Model_Order_Item $item
427     * @param array $qtys
428     * @return bool
429     */
430    protected function _needToAddDummy($item, $qtys) {
431        if ($item->getHasChildren()) {
432            foreach ($item->getChildrenItems() as $child) {
433                if (isset($qtys[$child->getId()]) && $qtys[$child->getId()] > 0) {
434                    return true;
435                }
436            }
437            return false;
438        } else if($item->getParentItem()) {
439            if (isset($qtys[$item->getParentItem()->getId()]) && $qtys[$item->getParentItem()->getId()] > 0) {
440                return true;
441            }
442            return false;
443        }
444    }
445
446    /**
447     * Decides if we need to create dummy shipment item or not
448     * for eaxample we don't need create dummy parent if all
449     * children are not in process
450     *
451     * @deprecated after 1.4, Mage_Sales_Model_Service_Order used
452     * @param Mage_Sales_Model_Order_Item $item
453     * @param array $qtys
454     * @return bool
455     */
456    protected function _needToAddDummyForShipment($item, $qtys) {
457        if ($item->getHasChildren()) {
458            foreach ($item->getChildrenItems() as $child) {
459                if ($child->getIsVirtual()) {
460                    continue;
461                }
462                if (isset($qtys[$child->getId()]) && $qtys[$child->getId()] > 0) {
463                    return true;
464                }
465            }
466            if ($item->isShipSeparately()) {
467                return true;
468            }
469            return false;
470        } else if($item->getParentItem()) {
471            if ($item->getIsVirtual()) {
472                return false;
473            }
474            if (isset($qtys[$item->getParentItem()->getId()]) && $qtys[$item->getParentItem()->getId()] > 0) {
475                return true;
476            }
477            return false;
478        }
479    }
480
481}