Rozszerzenie typu złożonego o nazwie „imageType” o niestandardowy typ obrazu

22

Celem modułu, który obecnie opracowuję, jest dodanie niestandardowego typu obrazu o nazwie „opengraph_image”. Dodałem nowy atrybut EAV przez mój skrypt InstallData.php, który działa dobrze. Kiedy teraz loguję się do backendu Magento2 i zmieniam produkt, mogę wybrać typ obrazu „opengraph_image” podczas przesyłania lub edycji zdjęć produktu.

Jednak na froncie chciałbym wyświetlić ten obraz. Dlatego utworzyłem plik etc / view.xml w moim module o następującej treści:

<?xml version="1.0"?>
<view xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:module:Esites_SEO:etc/custom.xsd">
    <media>
        <images module="Magento_Catalog">
            <image id="opengraph_image" type="opengraph_image">
                <width>265</width>
                <height>265</height>
            </image>
        </images>
    </media>
</view>

Ale teraz pojawia się następujący błąd:

Invalid XML in file /var/www/html/vhosts/magento2/app/code/Esites/SEO/etc/view.xml:
Element 'image', attribute 'type': [facet 'enumeration'] The value 'opengraph_image' is not an element of the set {'thumbnail', 'small_image', 'image', 'swatch_image', 'swatch_thumb'}.
Line: 5

Element 'image', attribute 'type': 'opengraph_image' is not a valid value of the local atomic type.
Line: 5

Powodem jest to, że nie ładuje mojego pliku custom.xsd znajdującego się w: app/code/Esites/SEO/etc/custom.xsdgdzie definiuję opengraph_image. Zamiast tego wydaje się, że po prostu ładuje to domyślny plik XSD:vendor/magento/framework/Config/etc/view.xsd

Zawartość mojego pliku custom.xsd jest kopią (do celów testowych) tego oryginalnego pliku view.xsd, w którym w wierszu 75 dodałem:

 <xs:enumeration value="opengraph_image"/>

Frontend działa bez błędów, jeśli dołączę powyższą linię do oryginalnego pliku view.xsd. Postępowałem zgodnie z dokumentacją: http://devdocs.magento.com/guides/v2.0/extension-dev-guide/build/XSD-XML-validation.html, a moje ścieżki są budowane zgodnie z informacjami na tej stronie. Pamięć podręczna jest czyszczona wiele razy.

czego mi brakuje?

langezwieper
źródło
Próbowałeś zmienić się module="Magento_Catalog" na module="Esites_SEO"?
Raphael w Digital Pianism

Odpowiedzi:

9

Magento2 ładuje domyślny view.xsd, ponieważ program ConfigView Reader używa lib/internal/Magento/Framework/Config/SchemaLocator.phpi zwraca wartość domyślnąview.xsd

$this->schema = $urnResolver
    ->getRealPath('urn:magento:framework:Config/etc/view.xsd');`

Byłem w stanie to zmienić, wykonując poniższe kroki:

  • Utwórz nowe rozszerzenie, na przykład Magento_SampleMinimal
  • Utwórz definicję wtyczki w {MODULE}/etc/di.xml

    <?xml version="1.0"?>
    <config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:ObjectManager/etc/config.xsd">
        <type name="Magento\Framework\Config\SchemaLocator">
            <plugin name="SampleMinimal_SchemaLocator" type="Magento\SampleMinimal\Model\Plugin\SchemaLocator" sortOrder="1"/>
        </type>
    </config>
  • Utwórz wtyczkę w {MODULE} /Model/Plugin/SchemaLocator.php

    <?php
    namespace Magento\SampleMinimal\Model\Plugin;
    
    use Magento\TestFramework\ObjectManager;
    
    class SchemaLocator
    {
        /**
         * After Get Schema
         *
         * @param \Magento\Framework\Config\SchemaLocator $schemaLocator
         * @param string $result
         * @return array
         */
        public function afterGetSchema(\Magento\Framework\Config\SchemaLocator $schemaLocator, $result)
        {
            $result = sprintf(realpath(__DIR__ . '/../../etc/view.xsd'));
            return $result;
        }
    }

    Aktualizacja dla Magento 2.0. wersja

  • Skopiuj lib/internal/Magento/Framework/Config/etc/view.xsddo{MODULE}/etc/view.xsd

Dla Magento 2.1. wersja, skopiujVendor/Magento/Framework/Config/etc/view.xsddo{MODULE}/etc/view.xsd * Edytuj{MODULE}/etc/view.xsdi dodaj nowy typmedia_attribute

Jarosław Woronoj
źródło
Mówisz poważnie ... Czy to jedyny sposób? Wydaje się przesadne i prawdopodobnie śmieszne, że nie można dodać własnego obrazu bez nadpisania rdzenia XSD
Erfan
To właściwe rozwiązanie. Wielkie dzięki za ten Jarosław.
medyna,
To wspaniale, dziękuję! Polecam jednak napisanie wtyczki, Magento\Framework\Config\Dom\UrnResolverponieważ są miejsca, które używają jej bezpośrednio zamiast przechodzić SchemaLocator.
szybka zmiana w
0

To wydaje się być wadą projektową w połączeniu z błędem Magento 2. Utworzyłem tutaj raport o błędzie: https://github.com/magento/magento2/issues/10161

Jeśli używasz konstruktora obrazów bezpośrednio w szablonie do generowania obrazu opengraph_image, lepszym rozwiązaniem jest przekazanie niestandardowych atrybutów (za pomocą Magento\Catalog\Block\Product\ImageBuilder::setAttributeslub trzeciego parametru Magento\Catalog\Block\Product\View::getImage).

Jednak to nie zadziała (biorąc pod uwagę mój raport o błędach), więc nadal będziesz musiał zastąpić createmetodę ImageBuilder, aby przekazać te atrybuty do programu Image Image Helper.

Erfan
źródło
0

Jest prostszy sposób niż odpowiedź Jarosława. Można zmienić parametry konstruktora na SchemaLocator w pliku di.xml modułu. Lubić:

<type name="Magento\Framework\Config\SchemaLocator" >
    <arguments>
        <argument name="realPath" xsi:type="string">urn:magento:module:VendorName_ModuleName:etc/view.xsd</argument>
    </arguments>
</type>

Nie potrzebujesz wtyczki.

David Stone
źródło
Uwaga, to rozwiązanie działa tylko wtedy, gdy masz $ realPath jako argument w SchemaLocator. Zależy od wersji Magento 2.
Pol Ravalitera
-1

Nie musisz go modyfikować ani zastępować view.xsd, ten plik służy wyłącznie do sprawdzania poprawności.
Niedawno zaimplementowałem moje rozwiązanie, wykonując następujące czynności: Utwórz atrybut katalogu obrazów (powiedzmy, że nowy atrybut o identyfikatorze 162). Po utworzeniu atrybutu będziesz mógł zastosować go do dowolnego obrazu katalogu. Teraz musisz zastosować odpowiedni model i widoczność z przodu. Możesz to zrobić programowo lub postępując zgodnie z tym przewodnikiem.

  1. Otwórz bazę danych za pomocą phpMyAdmin lub MySQL i spróbuj wykonać kopię lustrzaną dowolnego atrybutu systemowego, takiego jak small_image

    use magento2_database_name;
    SELECT * FROM  `eav_attribute`;
    UPDATE `magento2_database_name`.`eav_attribute` SET `frontend_model` = 'Magento\\Catalog\\Model\\Product\\Attribute\\Frontend\\Image' WHERE  `eav_attribute`.`attribute_id` =162;
    SELECT * FROM  `catalog_eav_attribute`;
    UPDATE `magento2_database_name`.`catalog_eav_attribute` SET `is_visible` = '1', 'using_in_product_listing' = '1' WHERE `catalog_eav_attribute`.`attribute_id` =162;
  2. Przejdź do www_root/magento2_root/app/design/frontend/Theme/package/etc/view.xmli dodaj nowy typ obrazu:

        <image id="opengraph_image" type="opengraph_image">
            <width>265</width>
            <height>265</height>
        </image>
  3. Zaktualizuj pliki szablonów, dodając nowy typ obrazu www_root/magento2_root/app/design/frontend/Theme/package/Magento_Catalog/templates/product/
  4. Wyczyść pamięć podręczną, a zobaczysz ją z przodu.

Dla mnie zadziałało najechanie kursorem na listę produktów kategorii, mam nadzieję, że ta pomoc.

JROCA22
źródło
dzięki 7ochem, to mój pierwszy prawdziwy post.
JROCA22
To rozwiązanie nie działa, ponieważ Magento aktywnie sprawdza poprawność XSD
barbazul
@barbazul to tylko wtedy, gdy jesteś w trybie programisty, jeśli dobrze pamiętam.
Erfan
@Erfan To może być. Szczerze nie sprawdziłem. Ale nadal jest to znak, że nie tak należy to robić lub że w tym konkretnym XSD jest coś nie tak
barbazul
Może nie jest to najlepsza praktyka, ale dla mnie
zadziałała