Magento 1: tại sao một số phương thức quan sát gọi getEvent () và một số không?


8

Một cái gì đó tôi nhận thấy gần đây và tôi tò mò về nó.

Ví dụ 1: việc sử dụng getEvent()

Trong Mage_Core_Model_Localetrong setLocale()phương pháp, một sự kiện được gửi đi:

Mage::dispatchEvent('core_locale_set_locale', array('locale'=>$this));

Một người quan sát cho sự kiện này là bindLocale()từMage_Adminhtml_Model_Observer

public function bindLocale($observer)
{
    if ($locale=$observer->getEvent()->getLocale()) {
        if ($choosedLocale = Mage::getSingleton('adminhtml/session')->getLocale()) {
            $locale->setLocaleCode($choosedLocale);
        }
    }
    return $this;
}

Vì vậy, như bạn có thể thấy, để lấy lại miền địa phương, trước tiên chúng ta gọi getEvent()người quan sát.

Ví dụ 2: không có getEvent()

Trong Mage_Wishlist_Block_Customer_Wishlist_Item_Optionstrong __construct()phương pháp, một sự kiện được gửi đi:

Mage::dispatchEvent('product_option_renderer_init', array('block' => $this));

Vì vậy, chúng tôi đồng ý rằng cú pháp tương tự được sử dụng cho ví dụ 1 và 2.

Tuy nhiên, một người quan sát cho ví dụ thứ hai này là initOptionRenderer()từMage_Bundle_Model_Observer

public function initOptionRenderer(Varien_Event_Observer $observer)
{
    $block = $observer->getBlock();
    $block->addOptionsRenderCfg('bundle', 'bundle/catalog_product_configuration');
    return $this;
}

Và như bạn có thể thấy, để lấy lại khối, chúng tôi không gọi getEvent()cho người quan sát

Câu hỏi

  • Tại sao getEvent()phương thức được gọi trong ví dụ # 1? Hoặc tại sao getEvent()không được gọi trong ví dụ # 2?
  • Mục đích của getEvent()phương pháp là gì?
  • Nên sử dụng getEvent()ở đâu và không nên sử dụng ở đâu?

Câu trả lời:


7

Nó có thể có lý do lịch sử, đạt trở lại ngoài phiên bản 1.0.

Đối Varien_Eventtượng là nơi logic để chứa các tham số cho một sự kiện cụ thể, nhưng vì Magento chuyển một Varien_Observerđối tượng cho tất cả các phương thức quan sát viên, nên lối tắt truy cập các tham số có ý nghĩa (và nó đã ở đó ít nhất là từ 1.1).

Tôi thực sự không thấy bất kỳ giá trị nào trong hai đối tượng khác nhau khi chúng được sử dụng ngày nay .

Nhưng rõ ràng nó đã không được lên kế hoạch như vậy ngay từ đầu. Trong phương thức Mage::addObserver(), không chỉ tên sự kiện và tên người quan sát và đối số tĩnh từ <args>nút XML được đặt, mà còn gọi lại:

$observer->setName($observerName)->addData($data)->setEventName($eventName)->setCallback($callback);

Bằng cách này, các nhà quan sát có thể tự gửi đi, với $observer->dispatch($event). Trong trường hợp đó, người quan sát sẽ không có dữ liệu sự kiện trên chính họ và bạn sẽ cần bạn sử dụng getEvent()để truy cập nó. Nhưng phương pháp này không được sử dụng ở bất cứ đâu, vì vậy trong thực tế, nó không thành vấn đề.

Nếu bạn muốn thực hành một số khảo cổ học phần mềm và đào sâu hơn, bạn sẽ tìm thấy nhiều mã chết hơn gợi ý về những ý tưởng ban đầu chưa bao giờ biến nó thành sản phẩm cuối cùng, như Varien_Event_Observer_Collection.


Cảm ơn bạn. Sẽ đề cập đến các khía cạnh "lịch sử". Có vẻ như bạn đã làm điều đó cho chúng tôi :)
Rajeev K Tomy

8

Một điều rõ ràng.

Gọi $observer->getEvent()->getSomething()$observer->getSomething()trả lại điều tương tự.

Hãy xem Mage_Core_Model_App::dispatchEventphương pháp.

Tại một thời điểm bạn có $event = new Varien_Event($args);nơi $argslà các đối số truyền cho dispatchEventphương pháp.
Varien_Eventmở rộng Varien_Objectđể bạn có thể truy cập một cách kỳ diệu các yếu tố $argstừ Varien_Eventví dụ.

nhưng cũng có dòng này $observer->addData($args);ở đâu $argslà những điều tương tự như trên.

Varien_Event_Observercũng mở rộng Varien_Objectđể điều này cho phép bạn truy cập các phần tử một cách kỳ diệu $argsthông qua đối tượng Observer.

Phần kết luận:

Thành $_dataviên trong lớp Người quan sát và lớp Sự kiện chứa loại tương tự. Người quan sát có thêm một vài lĩnh vực khác. như event, event_name.

Hãy nói $argsnhư thế này:

array(
   'some_arg' => 'someArg',
   'other_arg' => 'otherArg',
)

Khi gửi sự kiện, $_datađối tượng trong Sự kiện sẽ trông như thế này:

array(
   'some_arg' => 'someArg',
   'other_arg' => 'otherArg',
   'name' => 'event name here'
)

và trong lớp Người quan sát sẽ trông như thế này:

array(
   'some_arg' => 'someArg',
   'other_arg' => 'otherArg',
   'event_name' => 'event name here',
   'event' => instance of Varien_event,
   'callback' => ..., 
   'name' => 'observer name here'
)

Nhưng tôi không thể trả lời tại sao sự thiếu nhất quán này tồn tại.
Tôi chỉ có thể suy đoán rằng mã được viết bởi 2 nhà phát triển khác nhau.
Nếu nó có giá trị gì đó, tôi luôn luôn sử dụng $observer->getEvent()->getSomething().

[BIÊN TẬP]

Tại sao phương thức getEvent () được gọi trong ví dụ # 1? Hoặc tại sao getEvent () không được gọi trong ví dụ # 2?

Thiếu tính nhất quán

Mục đích của phương thức getEvent () là gì?

Đối Varien_Eventtượng phải là đối tượng trình bao bọc đối với các đối số được truyền cho người quan sát

Nơi nào nên sử dụng getEvent () và nơi nào không nên sử dụng? Sử dụng chúng như bạn muốn. Bạn sẽ nhận được kết quả tương tự mọi lúc.


Nhận được lời giải thích về sự thiếu nhất quán, hãy xem câu trả lời của tôi
Raphael tại Digital Pianism

Tôi luôn luôn $observer->getEvent()muốn lấy bất kỳ dữ liệu nào trong người quan sát. Tôi biết chúng ta có thể lấy dữ liệu từ $observertrực tiếp. Nhưng tôi không làm điều đó bởi vì tôi luôn cảm thấy, việc tiêm đối tượng Varien_Eventlà rất cụ thể để giữ dữ liệu sự kiện. Do đó tôi luôn phụ thuộc vào đối tượng sự kiện. Tôi cảm thấy đó là cách tiếp cận chính xác.
Rajeev K Tomy

@RajeevKTomy xem câu trả lời của tôi, thực sự không có điểm nào để sử dụng getEvent()ngoại trừ nếu bạn cần tên sự kiện HOẶC muốn tương thích Magento 1.0
Raphael tại Digital Pianism

3

Giải thích về sự thiếu nhất quán.

Theo Vinai và những gì Vitaly Korotun đã nói với anh ta vào một lúc nào đó:

getEvent()là di sản. Quay lại Magento 1.0 ngày , dữ liệu sự kiện không thể được lấy trực tiếp từ người quan sát.

Vì vậy, nếu bạn không cần phải nhận event_namevà không quan tâm quá nhiều về việc mã của bạn tương thích với Magento 1.0, bạn có thể bỏ qua getEvent().

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.