Why is magento 2 creating directives for media images using the admin url?

for example when i add an image on category page WYSIWYG it adds

<img src="{{media url="wysiwyg/image.jpg"}}" alt="" />

but then magento parses it for frontend and is like this

<img src="https://domain.co.uk/admin/cms/wysiwyg/directive/___directive/e3ttZWRpYSB1cmw9Ind5c2l3eWcvQ29udmV5b3JfYmVsdHNfZmFzdF9kZWxpdmVyeS5qcGcifX0,/key/b67d0a8069ef28a8443e0bad6d912512704213d60e1d9021b1ec2b9dd34bf390/" alt="">

because its linking to admin the only way it will load on browser is if you are logged in to the admin. This also poses a security issue because it is disclosing the admin path on frontend.

I looked in vendor/magento/module-cms/Helper//Wysiwyg/images.php and looks like the function getImageHtmlDeclaration() generates this

   public function getImageHtmlDeclaration($filename, $renderAsTag = false)
    {
        $fileurl = $this->getCurrentUrl() . $filename;
        $mediaUrl = $this->_storeManager->getStore()->getBaseUrl(\Magento\Framework\UrlInterface::URL_TYPE_MEDIA);
        $mediaPath = str_replace($mediaUrl, '', $fileurl);
        $directive = sprintf('{{media url="%s"}}', $mediaPath);
        if ($renderAsTag) {
            $html = sprintf('<img src="%s" alt="" />', $this->isUsingStaticUrlsAllowed() ? $fileurl : $directive);
        } else {
            if ($this->isUsingStaticUrlsAllowed()) {
                $html = $fileurl; // $mediaPath;
            } else {
                $directive = $this->urlEncoder->encode($directive);
                $html = $this->_backendData->getUrl('cms/wysiwyg/directive', ['___directive' => $directive]);
            }
        }
        return $html;
    }

I tried to use static urls for media but still no use so the only work around I can think of is to edit this function to use frontend url instead of backend/admin

any help on this would be very much appreciated :)

  • Images in the wysiwyg editor appear to use the 'admin/cms/wysiwyg/directive' URLs when you look at the tags in the 'Edit HTML Source' window, but on the frontend you should be see a 'pub/static/wysiwyg/' URL for those same images. – Aaron Allen Jan 16 '17 at 8:45
  • the admin/cms/wysiwyg/directive is on frontend on my magento 2 install – Steve B Jan 16 '17 at 18:12
  • I'm facing same issue. Magento 2.1.2 WYSIWYG is creating admin URL for images for me as well. – Ejaz Jan 17 '17 at 12:22
  • Any news on this? – simonthesorcerer Jan 18 '17 at 17:41
  • 2
    After many hours on this last night, the best recommendation (certainly not a solution) on this is to click the "Show/Hide Editor" button before save. When turning off the WYSIWYG editor, Magento will convert the directive URL to the {{media url="wysiwyg/some-image.jpg"}} format we have come to expect in Magento – Darren Felton Feb 7 '17 at 13:39

This is a known bug which is still present in CE 2.1.5.

The known fix is to add 'add_directives' => true to getConfig function ofvendor/magento/module-cms/Model/Wysiwyg/Config.php.

The best way to do that is to write an interceptor.

  1. In your custom Magento 2 extension's etc/di.xml file:

    <config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:ObjectManager/etc/config.xsd">
      <type name="Magento\Cms\Model\Wysiwyg\Config">
       <plugin name="add_wysiwyg_data" type="Vendor\Module\Plugin\WysiwygConfig" sortOrder="30" />
      </type>
    </config>
    
  2. Vendor\Module\Plugin\WysiwygConfig.php:

    namespace Vendor\Module\Plugin;
    
    class WysiwygConfig
    {
     public function afterGetConfig($subject, \Magento\Framework\DataObject $config)
     {
       $config->addData([
        'add_directives' => true,
       ]);
    
       return $config;
     }
    }
    
  3. Install it php bin/magento setup:upgrade

  4. Important: after installation you need to re-edit the affected category descriptions and re-upload images.

Idea of this fix extension is not mine but this guy. He also packed it all up on github for you to download.

I tested it myself on CE 2.1.4 and it works fine.

The simplest solution is to update the getImageHtmlDeclaration() function in vendor/magento/module-cms/Helper//Wysiwyg/images.php

public function getImageHtmlDeclaration($filename, $renderAsTag = false)
{
    $fileurl = $this->getCurrentUrl() . $filename;
    $mediaUrl = $this->_storeManager->getStore()->getBaseUrl(\Magento\Framework\UrlInterface::URL_TYPE_MEDIA);
    $mediaPath = str_replace($mediaUrl, '', $fileurl);
    $directive = sprintf('{{media url="%s"}}', $mediaPath);
    if ($renderAsTag) {
        $html = sprintf('<img src="%s" alt="" />', $this->isUsingStaticUrlsAllowed() ? $fileurl : $directive);
    } else {
         $html = $fileurl;
        //if ($this->isUsingStaticUrlsAllowed()) {
        //    $html = $fileurl; // $mediaPath;
        //} else {
        //    $directive = $this->urlEncoder->encode($directive);
        //    $html = $this->_backendData->getUrl('cms/wysiwyg/directive', ['___directive' => $directive]);
        //}
    }
    return $html;
}

This may not be the best approach, but it works.

I got the same issue with CE 1.9 And here is the solution: the idea is trying to change variable $html (you can use Di, Plugin or Patch packagist.org/packages)

Magento\Cms\Helper\Wysiwyg\Images.php line 180

$html = $this->_backendData->getUrl('cms/wysiwyg/directive', ['___directive' => $directive]);

replace to

$html = $this->_backendData->getUrl(
                'cms/wysiwyg/directive',
                [
                    '___directive' => $directive,
                    '_escape_params' => false,
                ]
            );

Refer : github.com/PieterCappelle

In your custom Magento 2 extension's etc/di.xml file:

<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:ObjectManager/etc/config.xsd">
    <type name="Magento\Catalog\Observer\CatalogCheckIsUsingStaticUrlsAllowedObserver">
        <plugin name="cms_wysiwyg_images_static_urls_allowed_plugin" type="Vendor\Module\Plugin\CatalogCheckIsUsingStaticUrlsAllowedObserver" sortOrder="10" disabled="false"  />
    </type>
</config>

Vendor\Module\Plugin\CatalogCheckIsUsingStaticUrlsAllowedObserver.php

namespace Vendor\Module\Plugin;

class CatalogCheckIsUsingStaticUrlsAllowedObserver
{
    public function aroundExecute(
        \Magento\Catalog\Observer\CatalogCheckIsUsingStaticUrlsAllowedObserver $subject, 
        \Closure $proceed, 
        $observer)
    {
        $objectManager =  \Magento\Framework\App\ObjectManager::getInstance();        
        $storeManager  = $objectManager->get('\Magento\Store\Model\StoreManagerInterface');
        $catalogData  = $objectManager->get('\Magento\Catalog\Helper\Data');
        $storeID = $storeManager->getStore()->getStoreId(); 
        $result = $observer->getEvent()->getData('result');
        $result->isAllowed = $catalogData->setStoreId($storeID)->isUsingStaticUrlsAllowed();
    }
}

Working for me!

Your Answer

By clicking "Post Your Answer", you acknowledge that you have read our updated terms of service, privacy policy and cookie policy, and that your continued use of the website is subject to these policies.

Not the answer you're looking for? Browse other questions tagged or ask your own question.