Magento 2: Melewatkan Variabel dari Aksi Controller ke “View”

12

Di Magento 1, jika Anda ingin meneruskan data dari tindakan Pengontrol ke "Lihat" (yaitu blok di tata letak Anda, Anda bisa)

  1. Tambahkan nilai / objek ke registri global via Mage::register

  2. Langsung mengambil objek blok dan mengatur properti data pada objek blok yang diambil setelah berjalan loadLayout

  3. Metode panggilan pada objek blok dalam phtmlfile, dan memiliki objek blok menggunakan model / lapisan database untuk membaca data yang sebelumnya disimpan dalam aksi controller

Menggunakan metode objek blok untuk membaca dari database masih tampak berfungsi di Magento 2 - yang sesuai untuk beberapa jenis operasi. Namun,

  1. Tidak ada lagi pendaftaran global di Magento 2 (atau ada?)

  2. Sistem tata letak sekarang berfungsi dengan membuat objek halaman melalui pabrik, dan Anda tidak dapat mengambil referensi blok dengan cara yang sama seperti di Magento 1

Apakah mungkin di Magento 2 untuk meneruskan data langsung dari aksi pengontrol ke tampilan? Atau apakah ini pola yang terlalu langsung bagi dunia baru Design Pattern ™ Magento? Jika ini adalah pola yang terlalu langsung, apa yang harus dilakukan jika ada beberapa informasi terhitung yang ingin kami tampilkan dalam templat, tetapi tidak ingin menyimpan informasi itu ke dalam sistem stateful (yaitu kami tidak ingin menyimpannya ke basis data)

Saya dapat memikirkan beberapa cara berbeda untuk meretas ini bersama-sama - tetapi saya tertarik pada bagaimana Magento 2 ingin Anda melakukannya.

Catatan : Saya menyadari mungkin untuk mengambil contoh blok dalam aksi pengontrol menggunakan sesuatu seperti ini

$resultPage = $this->resultPageFactory->create();    
$block = $resultPage->getLayout()->getBlock('catalog.wysiwyg.js');        

var_dump(spl_object_hash($block));

Kode inti Magento 2 sering melakukan ini. Namun - objek blok yang diambil dalam objek pengontrol tampaknya merupakan objek yang berbeda dari yang tersedia di phtmltemplat melalui salah satu $thisatau $block(yang sebelumnya ( $this) tampaknya menjadi objek yang benar-benar merender templat, sedangkan yang nanti ( $block) tampaknya merupakan objek turunan dari tipe Blok Magento).

#File: path/to/template.phtml
var_dump(spl_object_hash($block));
var_dump(spl_object_hash($this));

Saya katakan "tampaknya" karena jika saya mengatur data dalam metode tindakan pengontrol, itu tidak tersedia di phtmltemplat - dan jika saya membandingkan spl_object_hashhasil di atas, saya mendapatkan tiga hash yang berbeda. Namun, saya cukup baru untuk semua ini bahwa di atas mungkin ada beberapa kesalahan lain yang saya buat - jadi jika Anda sudah bisa mengatur data pada blok dan mengambilnya dalam template saya ingin mendengarnya !

Alan Storm
sumber

Jawaban:

17

Mengenai # 1, registri masih ada, sangat mirip dengan apa yang Anda ketahui dari Magento 1. Hanya dipindahkan. Lihat:\Magento\Framework\Registry

Tambahkan ke konstruktor Anda melalui injeksi dependensi, dan kemudian Anda dapat menggunakan metode $registry->register($key, $value)dan familiar Anda $registry->registry($key)untuk menyimpan / mengakses data.

Saya akan merekomendasikan mencari-cari namespace \ Magento \ Framework jika Anda belum melakukannya. Banyak hal yang dapat diakses dari Mage atau App sebelumnya masih ada, hanya dipisahkan.

Sejauh praktik terbaik, saya tidak bisa menjawab itu, tapi saya berharap jawabannya adalah untuk menjaga logika sebanyak mungkin dari pengontrol. Melihat inti mungkin merupakan taruhan terbaik Anda. Misalnya, lihat halaman edit alamat pelanggan: Pengontrol dasar ; blok ekstensif - termasuk menarik ID alamat dan memuat, jika perlu. Mereka mengatasinya langsung di blok; mereka tidak melakukannya di controller dan kemudian menyebarkannya.

Ryan Hoerr
sumber
2
Triknya, tentu saja, adalah mengetahui bagian mana yang harus dilihat inti, dan yang harus diabaikan :) Terima kasih untuk petunjuknya, +1 untuk informasi yang bermanfaat!
Alan Storm
1
+1 untuk paragraf terakhir. Jika Anda perlu berbagi beberapa nilai yang dihitung, letakkan perilaku penghitungan untuk memisahkan objek dan menyebutnya dari blok yang memerlukan nilai itu. Registri tidak disarankan karena keadaan global bisa berubah dan Anda tidak pernah yakin apa yang akan Anda dapatkan dari sana. Mengatasi blok dari aksi langsung juga tidak disarankan karena Anda tidak pernah yakin apakah blok ada pada halaman (tata letak dapat membunuhnya)
Anton Kril
@AntonKril bagaimana dengan pembantu renderer halaman? Pembantu halaman CMS, pembantu tampilan produk, apakah itu dimaksudkan untuk memisahkan rendering dari permintaan HTTP?
Ivan Chepurnyi
5

Anda seharusnya tidak melewati Variabel dari Aksi Controller ke View. Gunakan blok ke untuk meneruskan Variabel ke Tampilan (mesin template).

KAndy
sumber
Mengapa? Bagaimana Anda bisa melewati get / post params dari block to view? Bukankah kebanyakan logika melewatkannya dari controller ke view?
LucScu
Gunakan Obyek Permintaan dalam blok. Jika Anda memblokir mendapatkan data dari pengontrol melalui Registry, Anda tidak dapat menggunakannya memblokir dengan pengontrol lain. Ini disebut penggabungan sementara dan praktik buruknya
KAndy
Saya menggunakan $ block-> assign () untuk meneruskan params permintaan dari controller ke block. Apakah ini juga praktik yang buruk?
LucScu
Mengatasi blok dari aksi langsung juga tidak disarankan karena Anda tidak pernah yakin apakah blok ada di halaman.
KAndy
Dalam kasus saya, saya yakin, karena ini adalah skenario khusus di mana pengontrol, tata letak dan blok hanya dikontrol oleh kode saya, jadi saya pikir ini adalah logika permintaan params dari pengontrol ke blok. Terima kasih atas balasan Anda!
LucScu