Chciałbym owinąć głowę przy użyciu atrybutów rozszerzenia, na przykład w przypadku cytatów.
Nie ma problemu z dodaniem niestandardowego atrybutu do takiej encji przy użyciu klasy konfiguracji jak w Magento 1, nie o to chodzi w tym pytaniu.
W tej chwili magia mnie przytłacza, gdy chcę ujawnić taki atrybut, który został dodany przez rozszerzenie poprzez interfejs API jednostek jako atrybut rozszerzenia.
AKTUALIZACJA : Wiem, jak powstają zwykłe fabryki. To pytanie dotyczy specjalnych fabryk, które tworzą instancje wygenerowanych implementacji dla wygenerowanych interfejsów atrybutów rozszerzenia.
Oto kroki, które podejmuję, aby to działało. Dodam je, aby ktokolwiek próbował odpowiedzieć, nie musiał wchodzić w te szczegóły.
Moje pytanie brzmi: JAK lub DLACZEGO działa.
Kroki ujawniania atrybutu rozszerzenia za pośrednictwem interfejsu API encji:
- Utwórz,
etc/extension_attributes.xml
który dodaje atrybut do interfejsu encji - Utwórz wtyczkę, aby dodać wartość atrybutu do
ExtensionAttributes
instancji encji .
Aby wykonać drugi punkt, ExtensionAttributes
potrzebna jest instancja encji . Z tego powodu wtyczka zależy od fabryki, którą menedżer obiektów dostarcza przez DI.
Do wyceny Magento\Quote\Api\Data\CartItemExtensionFactory
należy użyć przykładu.
Myślę, że rodzaj tej fabryki musi w jakiś sposób wyzwalać magię generacji.
Magento następnie generuje pasujący interfejs \Magento\Quote\Api\Data\CartItemExtensionInterface
z ustawiającymi i pobierającymi dla wszystkich atrybutów rozszerzenia.
Wydaje się jednak, że nie generuje konkretnej implementacji tego interfejsu. Przynajmniej PHPStorm tego nie widzi.
W jaki sposób Magento gromadzi informacje potrzebne do wygenerowania klasy? Jak można wywoływać wygenerowane metody interfejsu w konkretnej instancji? Czy jest to klasa generowana tylko w pamięci?
Cieszę się, że to działa, ale to nie jest naprawdę satysfakcjonujące. Zdolność Magentos do używania atrybutów tworzonych automatycznie przez rozszerzenia jest jednym z kluczowych czynników sukcesu. Jako programista modułów uważam, że potrzebuję dokładnego zrozumienia całego procesu.
Gdybym miał czas, po prostu zagłębiłbym się w to sam, ale wolałbym, gdybym tylko mógł uzyskać wyjaśnienie.
AKTUALIZACJA 2 : Trochę czasu zajęło mi przeczytanie \Magento\Framework\Api\Code\Generator\ExtensionAttributesInterfaceGenerator
i \Magento\Framework\Api\Code\Generator\ExtensionAttributesGenerator
. Teraz mam przynajmniej ogólne pojęcie o tym, co się dzieje. Jeśli nikt mnie nie pobije, napiszę opis pełnego procesu w pewnym momencie, ponieważ uważam, że byłoby to przydatne odniesienie.
Odpowiedzi:
Przede wszystkim autogeneration dzieje się na podstawie nazwy klasy przyrostka, np
Factory
,ExtensionInterface
(patrz\Magento\Framework\Api\Code\Generator\ExtensionAttributesInterfaceGenerator::EXTENSION_INTERFACE_SUFFIX
) lubExtension
(zobacz\Magento\Framework\Api\Code\Generator\ExtensionAttributesGenerator::EXTENSION_SUFFIX
).Właściwy generator jest wybierany na podstawie sufiksu tutaj
\Magento\Framework\Code\Generator::generateClass
.Załóżmy, że tryb Magento jest
developer
i brakujące klasy mogą być generowane w locie (podobny proces nastąpi, gdy zostanie użyty kompilator). Gdy menedżer obiektów próbuje utworzyć instancję, powiedzmy,Magento\Quote\Api\Data\CartItemExtensionFactory
i nie istnieje, następują:\Magento\Framework\Code\Generator\Autoloader::load
Factory
(lista wszystkich zadeklarowanych przyrostków znajduje się tutaj\Magento\Framework\ObjectManager\DefinitionFactory::getCodeGenerator
) i odpowiednia klasa generatora fabryki (Magento\Framework\ObjectManager\Code\Generator\Factory
) służy do generowania brakującej fabrykiFactory
sufiksu, tak będzieMagento\Quote\Api\Data\CartItemExtension
. Ta klasa nie istnieje i autogeneracja jest ponownie wywoływana przez autoloader, ale tym razem dla klasy ExtensionExtension
i\Magento\Framework\Api\Code\Generator\ExtensionAttributesGenerator
będzie używany do generowania tej klasyMagento\Quote\Api\Data\CartItemInterface
, ponieważ istnieje i klasa rozszerzenia została pomyślnie wygenerowana. Jednak przy próbie dołączenia pliku klasy rozszerzenia automatyczne generowanie jest ponownie uruchamiane, ponieważMagento\Quote\Api\Data\CartItemExtension
implementujeMagento\Quote\Api\Data\CartItemExtensionInterface
, który nie istniejeExtensionInterface
i\Magento\Framework\Api\Code\Generator\ExtensionAttributesInterfaceGenerator
będzie używany do generowaniaextension_attributes.xml
, dostępnych za pośrednictwem\Magento\Framework\Api\ExtensionAttribute\Config
, a następnie generowane jest FactoryJedna ważna uwaga jest taka, że nie ma preferencji dla ExtensionInterface,
di.xml
ponieważ zarówno Extension, jak i ExtensionInterface są generowane automatycznie. Nie stanowi to problemu, ponieważ interfejs ExtentionInterface nie powinien być wstrzykiwany bezpośrednio przez konstrukt.źródło
Dla mnie dziś wieczorem, poza odpowiedzią z @Alex, widzę linie
w klasie
\Magento\Framework\Api\ExtensionAttributesFactory
tam, gdzie możemy chcieć rozpocząć debugowanie, jeśli interfejs rozszerzenia nie jest generowany. Prawie atrybuty rozszerzenia dotyczą strukturyzacji naszej klasy, tak jak tego oczekuje Magento 2.
te linie mówią:
to klasa w naszym rozszerzeniu atrybuty interfejsu
czy rozszerza \ Magento \ Framework \ Api \ ExtensibleDataInterface
ma ten interfejs funkcję o nazwie getExtensionAttributes
źródło