Question

I have a custom controller with below code.

namespace Vendor\Module\Controller\Service;
class Login extends \Magento\Framework\App\Action\Action{
protected $_storeManager;
protected $_customerFactory;
protected $_customerSession;
protected $_addressRepository;
protected $_addressDataFactory;
protected $addressFactory;
protected $customerRepository;
protected $checkoutSession;
private $logger;
protected $cart;
public function __construct(
    \Magento\Framework\App\Action\Context $context,
    \Magento\Store\Model\StoreManagerInterface $storeManager,
    \Magento\Customer\Model\CustomerFactory $customerFactory,
    \Magento\Customer\Model\Session $customerSession,
    \Magento\Checkout\Model\Session $checkoutSession,
    \Magento\Checkout\Model\Cart $cart,
    \Magento\Customer\Api\AddressRepositoryInterface $addressRepository,
    \Magento\Customer\Api\Data\AddressInterface $addressDataFactory,
    \Magento\Customer\Model\AddressFactory $addressFactory,
    \Magento\Customer\Api\CustomerRepositoryInterface $customerRepository,
    \Psr\Log\LoggerInterface $logger
) {
    $this->_storeManager     = $storeManager;
    $this->_customerFactory  = $customerFactory;
    $this->cart = $cart;
    $this->_customerSession = $customerSession;
    $this->_addressRepository = $addressRepository;
    $this->_addressDataFactory = $addressDataFactory;
    $this->_addressFactory = $addressFactory;
    $this->checkoutSession = $checkoutSession;
    $this->customerRepository = $customerRepository;
    $this->logger = $logger; 
    parent::__construct($context);
}

public function execute() {     
    $customerPin = $this->getRequest()->getParam('pin');
    echo $customerPin;die;

}

Above code reads the parameter pin from the url and display the parameter value.

http://www.example.com/test/service/login/pin/6

This works only if accessed in the same website. Suppose the controller is accessed like iframe, from the other domain. its showing blank screen.

is there any setting to be done? from research i found we need to set X-Frame-Options to make it work.

if so how that can be set from controller?

Can anyone look into this and update me the solution please.

Was it helpful?

Solution

I tried a few different versions of setHeader() but the only thing that worked for me was overwriting XFrameOptions.

  1. Vendor/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">
<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:ObjectManager/etc/config.xsd">

<!-- Preference type used, as we can't use a plugin on a __construct function -->
    <preference for="\Magento\Framework\App\Response\HeaderProvider\XFrameOptions" type="Vendor\Module\ResponseHeader\XFrameOptions" />
</config>
  1. Vendor/Module/ResponseHeader/XFrameOptions.php
<?php

namespace Vendor\Module\ResponseHeader;

class XFrameOptions extends \Magento\Framework\App\Response\HeaderProvider\XFrameOptions {

    public function __construct(
        $xFrameOpt = 'SAMEORIGIN',
        \Magento\Framework\App\Request\Http $request     
    ) {
        // Eg if your iframe controller frontname is 'test'
        $isIframeController = 
            ($request->getModuleName() == 'test');

        // Skip this for the iFrame page
        if ($isIframeController) {
            return;
        }
        return parent::__construct($xFrameOpt);        
    }    
}

This doesn't set the X-Frame-Header for the custom controller (eg "test"), but sets it for all other pages, so that your site is still protected against iFrame attacks.

OTHER TIPS

Assuming you have defined your webapi endpoint like this:

http://www.example.com/test/service/login/pin  

Then you can get the Post Value like this:

http://www.example.com/test/service/login/pin?pin=6

Otherwise, you will get a blank response when an endpoint is called inside an iframe.

I think you are trying to include a local environment into a iframe but that is not possible. The outside world can not access http://localsite/test/service/login/pin/6

Licensed under: CC-BY-SA with attribution
Not affiliated with magento.stackexchange
scroll top