#php #magento #overriding
#php #magento #переопределение
Вопрос:
Было много случаев, когда все, что я хотел сделать, это переопределить определенное действие на контроллере, но не все целиком. В большинстве случаев я просто переопределял весь контроллер, но мне интересно, есть ли способ получше? Есть ли у Magento способ просто переопределить одно действие в контроллере, оставив исходный контроллер и другие действия такими, какими они были?
Пример:
class Mage_Core_AwesomeController extends Mage_Core_Controller_Front_Action {
//has url of awesome/index
public function indexAction(){
//Some Awesome code
}
//has url of awesome/torewrite
public function torewriteAction(){
//Some Awesome code
}
}
class Local_Core_AwesomeController extends Mage_Core_AwesomeController {
//has url of awesome/torewrite
public function torewriteAction(){
//Some Awesome Override code
}
}
Таким образом, URL awesome / torewrite будет отправлен в Local_Core_AwesomeController, а url awesome / index будет отправлен в Mage_Core_AwesomeController.
Этот пример, очевидно, сфабрикован, он просто предназначен для того, чтобы показать, чего я хотел бы в теории. Поэтому, пожалуйста, не пытайтесь исправлять пример, просто продемонстрируйте лучший способ переопределить просто действие.
Я думаю, также было бы важно отметить, что я не хочу переписывать URL, просто переопределите действие. Может быть, это невозможно без перезаписи URL? Просто при перезаписи URL теги в макете меняются, и я бы предпочел оставить их прежними.
Комментарии:
1. Предположительно, вы можете сделать это таким образом: web-magician. blogspot.com/2009/06 / … — но эта функция, похоже, не работает. Хотя ответ здесь сработал отлично, хороший трюк.
Ответ №1:
В вашем Local/Core/etc/config.xml
определите свой контроллер в маршрутизаторе, который будет переопределен.
<config>
...
<frontend> // Use <admin> for backend routers
<routers>
<core> // <-- this is the router name
<args>
<modules>
<local_core before="Mage_Core">Local_Core</local_core>
</modules>
</args>
</core>
</routers>
</frontend>
...
</config>
Теперь Magento будет проверять Local/Core/controllers
перед Mage/Core/controllers
на наличие URL-адресов, начинающихся с core
(имя маршрутизатора). Ваш PHP-класс выше уже корректен.
На это лишь слегка намекается примерно на середине этой страницы, где говорится:
Начиная с Magento 1.3, вы можете просто добавить свой модуль к интерфейсному маршрутизатору. Перезаписи больше не нужны.
Комментарии:
1. круто, я попробую это проверить, спасибо! Просто из любопытства, позволяет ли это вам устанавливать своего рода цепочку приоритетов … так что проверьте local / core / controllers, затем community / core / controllers, затем mage / core / controllers? и он все равно будет запускать родительские действия правильно?
2. @sbditto85: Я почти уверен, что вам нужно будет вручную вызвать родительское действие с помощью чего-то вроде parent::indexAction . Кроме того, поскольку рендеринг макета запускается в действиях контроллера, вы де-факто застряли, выполняя свои действия в верхней части контроллера, а затем вызывая родительский файл в конце.
3. Извините, я неправильно истолковал вопрос как «это позволит вам запускать родительские действия?». Алан, как обычно, прав, вам нужно вызвать родительский элемент самостоятельно.
4. на самом деле я промахнулся … я имел в виду, что indexAction родительского класса вызывался бы, если бы он не присутствовал в дочернем классе … или мне пришлось бы переопределять все действия, а затем вызывать parrent ::(action)()?
5. Поскольку вы расширили основной контроллер, применяется обычное наследование PHP, вам не нужно указывать все действия. Если ваш класс не произошел от исходного контроллера, любые неуказанные действия все равно будут возвращены к оригиналу без каких-либо дальнейших усилий с вашей стороны.