Переопределить Magento Controller_Abstract

Мы изменили файл history.phtml Magento, чтобы отображались все заказы без каких-либо ограничений для веб-сайта с ограниченным доступом. Это работает, но мы столкнулись с проблемой при попытке распечатать или просмотреть заказ. Я отладил, и проблема заключается в Magento _canViewOrder (находится в Mage_Sales_Controller_Abstract). В этой функции реализована дополнительная и, конечно же, логическая проверка, чтобы проверить, может ли вошедший в систему пользователь просмотреть/распечатать запрошенный заказ:

if ($order->getId() && $order->getCustomerId() && ($order->getCustomerId() == $customerId)
            && in_array($order->getState(), $availableStates, $strict = true)

Поскольку у нас есть некоторая пользовательская разработка, нам нужно переопределить этот метод, чтобы снять ограничение. К сожалению, мы нигде не можем найти, как переопределить класс Controller.

Обратите внимание, что мы знаем, как переопределить маршрутизаторы/контроллеры, но этот находится в папке Controller и является абстрактным классом.

Может ли кто-нибудь указать мне правильное направление или предоставить мне образец config.xml для переопределения этого класса?


person JNDPNT    schedule 21.12.2012    source источник


Ответы (2)


Я решил использовать быстрый способ в конце концов. Я переопределил Mage_Sales_OrderController:

<?php
require_once Mage::getModuleDir('controllers', 'Mage_Sales') . DS . 'OrderController.php';
class MyCompany_MyModule_OrderController extends Mage_Sales_OrderController
{   
    /**
     * Check order view availability
     * Overridden from Mage_Sales_Controller_Abstract to
     * remove the customer restriction. We want to show all
     * orders to all customers on any time. 
     * 
     * TODO: Maybe in the future add a customer group restriction
     *
     * @param   Mage_Sales_Model_Order $order
     * @return  bool
     */
    protected function _canViewOrder($order)
    {
        $availableStates = Mage::getSingleton('sales/order_config')->getVisibleOnFrontStates();
        if ($order->getId() && in_array($order->getState(), $availableStates, $strict = true)) {
            return true;
        }

        return false;
    }
}

В моем config.xml я говорю Magento сначала использовать мой контроллер, а OrderController использовать в качестве резервного. Поскольку я переопределил только одну функцию, весь существующий код не будет затронут.

<?xml version="1.0"?>    
...

<frontend>
...
    <routers>
...
        <sales>
            <args>
                <modules>
                    <MyCompany_MyModule before="Mage_Sales_OrderController">MyCompany_MyModule_Sales</MyCompany_MyModule>
                </modules>
            </args>
        </sales>
    </routers>
...
</frontend>
...
person JNDPNT    schedule 21.12.2012

Вы можете переопределить любой класс, поместив его в app/code/local. При загрузке класса Magento сначала смотрит в локальный, затем в сообщество, затем в основной. Чтобы добиться желаемого, скопируйте файл в app/code/local/Mage/Sales/Controller/Abstract.php и внесите свои поправки.

Тем не менее, старайтесь избегать этого подхода, где это возможно, так как он может немного запутать, когда дело доходит до обновлений. Один из вариантов, который вы, возможно, захотите рассмотреть, — это изменение контроллера, расширяющего Mage_Sales_Controller_Abstract, и переопределение его метода _canViewOrder. См. здесь: http://drupal.org/project/magento

person james    schedule 21.12.2012
comment
Прежде всего: спасибо за ваш комментарий. Я знаю, что могу переопределить целые файлы таким образом, но я предпочитаю этого не делать. Мы всегда переопределяем файл в смысле расширения. Таким образом, нам нужно переопределить только один метод или большую часть времени мы можем просто использовать родителя, а затем делать что-то после него. Я пытаюсь переопределить контроллер внизу, пока мы говорим, но это наихудший вариант, ИМО. - person JNDPNT; 21.12.2012