We sacrifice by not doing any other technology, so that you get the best of Magento.

We sacrifice by not doing any other technology, so that you get the best of Magento.

    Magento 2: Change currency based on customer group using observer

    Vendor/Module/etc/frontend/events.xml

    <config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:Event/etc/events.xsd">
        <event name="controller_action_predispatch">
            <observer name="change_title_filter" instance="VendorModuleObserverCustomercurrency" />
        </event>
    </config>

    Vendor/Module/Observer/Customercurrency.php

    <?php
    
    namespace VendorModuleObserver;
    
    use MagentoFrameworkEventObserverInterface;
    use MagentoFrameworkEventObserver;
    use MagentoFrameworkViewLayoutInterface;
    
    class Customercurrency implements ObserverInterface
    {
        protected $context;
        public function __construct(
            MagentoCustomerModelSession $customerSession,
            MagentoFrameworkViewElementTemplate $context,
            MagentoFrameworkViewResultPage $resultPage,
            MagentoFrameworkViewPageConfig $pageConfig,
            MagentoStoreModelStoreManagerInterface $storeManager
    
        ) {
            $this->_customerSession = $customerSession;
            $this->pageConfig = $pageConfig;
            $this->resultPageFactory = $resultPage;
            $this->context = $context;
            $this->_storeManager = $storeManager;
        }  
        public function execute(MagentoFrameworkEventObserver $observer)
        {
            if($this->_customerSession->isLoggedIn()) {
                $customercurr = $this->helperData->getCurrenyCustomer();
                $customerGroup = $this->_customerSession->getCustomer()->getGroupId();
                $customergroupid = 1;
                if($customerGroup == $customergroupid){
                    $this->_storeManager->getStore()->setCurrentCurrencyCode('GBP');
                    break;
                }else{
                    $this->_storeManager->getStore()->setCurrentCurrencyCode('USD');
                }            
            }
        }
    }

     

     

    Magento 2 get current visitor Id for compare items

    Override the ListCompare block.

    Create Vendor/Module/etc/di.xml on your custom module

    <?xml version="1.0"?>
    <config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:ObjectManager/etc/config.xsd">
        <preference for="MagentoCatalogBlockProductCompareListCompare" type="VendorModuleBlockProductCompareListCompare" />
    </config>

    Create Vendor/Module/Block/Product/Compare/ListCompare.php

    <?php
    namespace VendorModuleBlockProductCompare;
    
    class ListCompare extends MagentoCatalogBlockProductCompareListCompare
    {
    	public function __construct(
            MagentoCatalogBlockProductContext $context,
            MagentoFrameworkUrlEncoderInterface $urlEncoder,
            MagentoCatalogModelResourceModelProductCompareItemCollectionFactory $itemCollectionFactory,
            MagentoCatalogModelProductVisibility $catalogProductVisibility,
            MagentoCustomerModelVisitor $customerVisitor,
            MagentoFrameworkAppHttpContext $httpContext,
            MagentoCustomerHelperSessionCurrentCustomer $currentCustomer,
            MagentoFrameworkObjectManagerInterface $objectManager,
            array $data = []
        ) {
        	$this->objectManager = $objectManager;
            parent::__construct($context,$urlEncoder,$itemCollectionFactory,$catalogProductVisibility,$customerVisitor,$httpContext,$currentCustomer,$data);
        }
    
    	/**
         * Retrieve Product Compare items collection
         *
         * @return MagentoCatalogModelResourceModelProductCompareItemCollection
         */
        public function getItems()
        {
        	if ($this->_items === null) {
                $this->_compareProduct->setAllowUsedFlat(false);
    
                $this->_items = $this->_itemCollectionFactory->create();
                $this->_items->useProductItem(true)->setStoreId($this->_storeManager->getStore()->getId());
    
                if ($this->httpContext->getValue(MagentoCustomerModelContext::CONTEXT_AUTH)) {
                    $this->_items->setCustomerId($this->currentCustomer->getCustomerId());
                } elseif ($this->_customerId) {
                    $this->_items->setCustomerId($this->_customerId);
                } else {
                	/****** Custom Code ******/
                    $sessionManager  = $this->objectManager->create('MagentoFrameworkSessionSessionManagerInterface');
                    $visitor = $sessionManager->getVisitorData();
                    if(!$this->_customerVisitor->getId() && isset($visitor['visitor_id'])){
                    	$visitorid = $visitor['visitor_id'];
                    }else{
                    	$visitorid = $this->_customerVisitor->getId();
                    }
                	/****** Custom Code ******/
                    $this->_items->setVisitorId($visitorid);
                }
    
                $this->_items->addAttributeToSelect(
                    $this->_catalogConfig->getProductAttributes()
                )->loadComparableAttributes()->addMinimalPrice()->addTaxPercents()->setVisibility(
                    $this->_catalogProductVisibility->getVisibleInSiteIds()
                );
            }
            return $this->_items;
        }
    }
    

     

    Magento 2 : How to Change Category Page Layout for Specific Category Only?

    Step 1: First you need to add the following file.

    appdesignfrontendMagemonkeysCustomthemeMagento_Cataloglayoutcatalog_category_view_id_{{id}}.xml

    NOTE: Here you need to replace {{id}} with real category id

    Now add the below code,

    <?xml version="1.0"?>
    <page xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" layout="2columns-left" xsi:noNamespaceSchemaLocation="urn:magento:framework:View/Layout/etc/page_configuration.xsd">
        <body>
            <referenceContainer name="columns.top">
                <container name="category.view.container" htmlTag="div" htmlClass="category-view" after="-">
                    <block class="MagentoCatalogBlockCategoryView" name="category.image" template="Magento_Catalog::category/image.phtml">
                        <arguments>
                            <argument name="image" xsi:type="object">MagentoCatalogViewModelCategoryImage</argument>
                            <argument name="output" xsi:type="object">MagentoCatalogViewModelCategoryOutput</argument>
                        </arguments>
                    </block>
                    <block class="MagentoCatalogBlockCategoryView" name="category.description" template="Magento_Catalog::category/description.phtml"/>
                    <block class="MagentoCatalogBlockCategoryView" name="category.cms" template="Magento_Catalog::category/cms.phtml"/>
                </container>
            </referenceContainer>
            <referenceContainer name="content">
                <block class="MagentoCatalogBlockCategoryView" name="category.products" template="Magento_Catalog::category/products.phtml">
                    <block class="MagentoCatalogBlockProductListProduct" name="category.products.list" as="product_list" template="Magento_Catalog::product/customlist.phtml">  <!-- Here you need to add your custom list file -->
                        <container name="category.product.list.additional" as="additional" />
                        <block class="MagentoFrameworkViewElementRendererList" name="category.product.type.details.renderers" as="details.renderers">
                            <block class="MagentoFrameworkViewElementTemplate" name="category.product.type.details.renderers.default" as="default"/>
                        </block>
                        <block class="MagentoCatalogBlockProductProductListItemContainer" name="category.product.addto" as="addto">
                            <block class="MagentoCatalogBlockProductProductListItemAddToCompare"
                                   name="category.product.addto.compare" as="compare"
                                   template="Magento_Catalog::product/list/addto/compare.phtml"/>
                        </block>
                        <block class="MagentoCatalogBlockProductProductListToolbar" name="product_list_toolbar" template="Magento_Catalog::product/list/toolbar.phtml">
                            <block class="MagentoThemeBlockHtmlPager" name="product_list_toolbar_pager"/>
                        </block>
                        <action method="setToolbarBlockName">
                            <argument name="name" xsi:type="string">product_list_toolbar</argument>
                        </action>
                    </block>
                </block>
                <block class="MagentoCookieBlockRequireCookie" name="require-cookie" template="Magento_Cookie::require_cookie.phtml">
                    <arguments>
                        <argument name="triggers" xsi:type="array">
                            <item name="compareProductLink" xsi:type="string">.action.tocompare</item>
                        </argument>
                    </arguments>
                </block>
            </referenceContainer>
            <referenceBlock name="page.main.title">
                <arguments>
                    <argument name="id" xsi:type="string">page-title-heading</argument>
                    <argument name="add_base_attribute_aria" xsi:type="string">page-title-heading toolbar-amount</argument>
                </arguments>
                <block class="MagentoCatalogBlockCategoryRssLink" name="rss.link" template="Magento_Catalog::category/rss.phtml"/>
            </referenceBlock>
        </body>
    </page>

    Step 2: Now you need to add the following file.

    appdesignfrontendMagemonkeysCustomthemeMagento_Catalogtemplatesproduct customlist.phtml

    Note: Now you can add your custom code or design in this file for your custom product list for a specific category. Hope that helps.

    How to delete all orders and sales related entry in Magento 2?

    This is a useful tip a programmer should follow before making the site go live. Because that time it will be better if the database won’t be having any dummy entries. So in case, if you wish to delete all orders and sales-related entries then follow the below commands.

        SET FOREIGN_KEY_CHECKS=0;
    
        TRUNCATE TABLE `sales_bestsellers_aggregated_daily`;
        TRUNCATE TABLE `sales_bestsellers_aggregated_monthly`;
        TRUNCATE TABLE `sales_bestsellers_aggregated_yearly`;
    
        TRUNCATE TABLE `sales_creditmemo`;
        TRUNCATE TABLE `sales_creditmemo_comment`;
        TRUNCATE TABLE `sales_creditmemo_grid`;
        TRUNCATE TABLE `sales_creditmemo_item`;
        TRUNCATE TABLE `sales_invoice`;
        TRUNCATE TABLE `sales_invoiced_aggregated`;
        TRUNCATE TABLE `sales_invoiced_aggregated_order`;
        TRUNCATE TABLE `sales_invoice_comment`;
        TRUNCATE TABLE `sales_invoice_grid`;
        TRUNCATE TABLE `sales_invoice_item`;
        TRUNCATE TABLE `sales_order`;
        TRUNCATE TABLE `sales_order_address`;
        TRUNCATE TABLE `sales_order_aggregated_created`;
        TRUNCATE TABLE `sales_order_aggregated_updated`;
        TRUNCATE TABLE `sales_order_grid`;
        TRUNCATE TABLE `sales_order_item`;
        TRUNCATE TABLE `sales_order_payment`;
        TRUNCATE TABLE `sales_order_status_history`;
        TRUNCATE TABLE `sales_order_tax`;
        TRUNCATE TABLE `sales_order_tax_item`;
        TRUNCATE TABLE `sales_payment_transaction`;
        TRUNCATE TABLE `sales_refunded_aggregated`;
        TRUNCATE TABLE `sales_refunded_aggregated_order`;
        TRUNCATE TABLE `sales_shipment`;
        TRUNCATE TABLE `sales_shipment_comment`;
        TRUNCATE TABLE `sales_shipment_grid`;
        TRUNCATE TABLE `sales_shipment_item`;
        TRUNCATE TABLE `sales_shipment_track`;
        TRUNCATE TABLE `sales_shipping_aggregated`;
        TRUNCATE TABLE `sales_shipping_aggregated_order`;
    
        TRUNCATE TABLE `quote`;
        TRUNCATE TABLE `quote_address`;
        TRUNCATE TABLE `quote_address_item`;
        TRUNCATE TABLE `quote_id_mask`;
        TRUNCATE TABLE `quote_item`;
        TRUNCATE TABLE `quote_item_option`;
        TRUNCATE TABLE `quote_payment`;
        TRUNCATE TABLE `quote_shipping_rate`;
    
        TRUNCATE TABLE sequence_invoice_1;
        TRUNCATE TABLE sequence_order_1;
        TRUNCATE TABLE sequence_shipment_1;
        TRUNCATE TABLE sequence_creditmemo_1;
    
        SET FOREIGN_KEY_CHECKS=1;

    That’s it.

    Magento 2: how to set critical CSS?

    Generally, Critical CSS sets inline in and defer all non-critical styles that are loaded asynchronously. So we can significantly improve the time to first render of site.

    The ‘critical’ CSS file should be located in app/design/frontend/themevendor/themename/web/css/critical.css

    After setting critical CSS, you need to enable it from the backend side. steps are Stores > Settings > Configuration > ADVANCED > Developer tab. Make sure this option does not show if production mode is enabled.

    In Magento default, the luma theme has critical.css so you can take reference from there, and here is the official doc in case if you wish to read further.

    Magento 2: Product qty box empty when edit product from cart in product detail page

    If you got the qty box empty when you edit the product from the cart page, please follow the below instruction.

    You need to override “vendor/magento/module-checkout/view/frontend/templates/cart/item/configure/updatecart.phtml” file in your theme

    <vendername>/<themename>/Magento_Checkout/templates/cart/item/configure/updatecart.phtml

    then just add below line in value

    <?= $block->getProductDefaultQty() * 1 ?>

    After making above changes QTY field code show will look like below:

    <input type="number"
    name="qty"
    id="qty"
    min="0"
    value="<?= $block->getProductDefaultQty() * 1 ?>"
    title="<?= $block->escapeHtmlAttr(__('Qty')) ?>"
    class="input-text qty"
    data-validate="<?= $block->escapeHtml(json_encode($block->getQuantityValidators())) ?>"/>

    Note: I have tried this in Magento 2.3.6 – Let us know if it works with the other versions as well.

    How to print log with new custom file in Magento 2?

    If you want to print your code log in the custom log file, then use the below mention code to print the log in the custom log file.

    $StringVar = 'Magemonkeys';
    $ArrayVar = array('Magemonkeys', 'Abbacus');
    
    $writer = new ZendLogWriterStream(BP . '/var/log/CustomFileName.log');
    $logger = new ZendLogLogger();
    $logger->addWriter($writer);
    
    $logger->info('Lorem ipsum dolor sit amet...'); // For print simple text in custom log file
    $logger->info($StringVar); // For print string in custom log file
    $logger->info(print_r($ArrayVar, true)); // For print array in custom log file

    That’s it.

    Refresh your page and see your custom log file in Magento /var/log directory. Hope that helps.

    Magento 2: Show message on every page using message manager

    Display the new message and clear the previous messages on every page using Message Manager.

    Create the event.xml in your module and add the below code

    <?xml version="1.0"?>
    <config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:Event/etc/events.xsd">
        <event name="layout_render_before">
          <observer name="success_message" instance="VendorModuleObserverMessageObserver" shared="false" />
      </event>
    </config>

    Create the MessageObserver.php file in the Observer directory

    <?php
    namespace VendorModuleObserver;
    
    use MagentoFrameworkEventObserverInterface;
    use MagentoFrameworkEventObserver;
    
    class MessageObserver implements ObserverInterface
    {
        public function __construct(       
            MagentoFrameworkMessageManagerInterface $messageManager,
        )
        {    
            $this->messageManager = $messageManager;   
        }
        public function execute(Observer $observer)
        {
            $this->messageManager->getMessages(true); //this will clear your messageManager container
            $this->messageManager->addSuccess(__('Add Custom message here'));
            return $this;
        }
    }

     

    Magento 2 – How to programmatically check user is subscribed for newsletter or not?

    Use Factory,
    MagentoNewsletterModelSubscriberFactory

    Using isSubscribed() method. You can check the user is a subscriber to the newsletter or not.

    <?php
    namespace MagemonkeySubscriberModel;
    
    use MagentoFrameworkExceptionLocalizedException;
    use MagentoNewsletterModelSubscriberFactory;
    
    class IsSubscribed
    {
        /**
         * @var SubscriberFactory
         */
        private $subscriberFactory;
    
        /**
         * @param SubscriberFactory $subscriberFactory
         */
        public function __construct(
            SubscriberFactory $subscriberFactory
        ) {
            $this->subscriberFactory = $subscriberFactory;
        }
    
        /**
         * @param int $customerId
         * @return bool
         */
        public function isCustomerSubscribeById($customerId) {
            $status = $this->subscriberFactory->create()->loadByCustomerId((int)$customerId)->isSubscribed();
    
            return (bool)$status;
        }
    
        /**
         * @param string $email
         * @return bool
         */
        public function isCustomerSubscribeByEmail($email) {
            $status = $this->subscriberFactory->create()->loadByEmail($email)->isSubscribed();
    
            return (bool)$status;
        }
    }

     

    add extra field to newsletter subscription module magento2

    The newsletter subscription module in Magento has only one field (email) by default. If you want to add  an extra field to the form (like the name), perform the following steps:

    Magemonkeys/Newsletter/registration.php

    <?php
    MagentoFrameworkComponentComponentRegistrar::register(
    	MagentoFrameworkComponentComponentRegistrar::MODULE,
    	'Magemonkeys_Newsletter',
    	__DIR__
    );
    

    Magemonkeys/Newsletter/etc/module.xml

    <?xml version="1.0"?>
    <config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:Module/etc/module.xsd">
        <module name="Magemonkeys_Newsletter" setup_version="1.0.0"/>
        <sequence>
          <module name="Magento_Newsletter" />
        </sequence>
    </config>
    

    Magemonkeys/Newsletter/Setup/InstallSchema.php

    <?php
    
    namespace MagemonkeysNewsletterSetup;
    
    use MagentoFrameworkDBDdlTable;
    use MagentoFrameworkSetupInstallSchemaInterface;
    use MagentoFrameworkSetupModuleContextInterface;
    use MagentoFrameworkSetupSchemaSetupInterface;
    
    class InstallSchema implements InstallSchemaInterface {
    	public function install(SchemaSetupInterface $setup, ModuleContextInterface $context) {
    		$setup->startSetup();
    
    		$table = $setup->getTable('newsletter_subscriber');
    
    		$setup->getConnection()->addColumn(
    			$table,
    			'full_name',
    			[
    				'type' => Table::TYPE_TEXT,
    				'nullable' => true,
    				'comment' => 'Name',
    			]
    		);
    
    		$setup->endSetup();
    	}
    }

    Magemonkeys/Newsletter/etc/di.xml

    <?xml version="1.0"?>
    <config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../lib/internal/Magento/Framework/ObjectManager/etc/config.xsd">
      <preference for="MagentoNewsletterControllerSubscriberNewAction" type="MagemonkeysNewsletterControllerSubscriberNewAction" />
    </config>
    

    Magemonkeys/Newsletter/Controller/Subscriber/NewAction.php

    <?php
    
    namespace MagemonkeysNewsletterControllerSubscriber;
    
    use MagentoCustomerApiAccountManagementInterface as CustomerAccountManagement;
    use MagentoCustomerModelSession;
    use MagentoCustomerModelUrl as CustomerUrl;
    use MagentoFrameworkAppActionContext;
    use MagentoFrameworkControllerResultFactory;
    use MagentoFrameworkControllerResultRedirect;
    use MagentoFrameworkExceptionLocalizedException;
    use MagentoFrameworkPhrase;
    use MagentoNewsletterControllerSubscriberNewAction as SubscriberNewController;
    use MagentoNewsletterModelSubscriber;
    use MagentoNewsletterModelSubscriberFactory;
    use MagentoNewsletterModelSubscriptionManagerInterface;
    use MagentoStoreModelStoreManagerInterface;
    
    /**
     * New newsletter subscription action
     *
     * @SuppressWarnings(PHPMD.CouplingBetweenObjects)
     */
    class NewAction extends SubscriberNewController {
    
    	/**
    	 * @var SubscriptionManagerInterface
    	 */
    	private $subscriptionManager;
    
    	/**
    	 * Initialize dependencies.
    	 *
    	 * @param Context $context
    	 * @param SubscriberFactory $subscriberFactory
    	 * @param Session $customerSession
    	 * @param StoreManagerInterface $storeManager
    	 * @param CustomerUrl $customerUrl
    	 * @param CustomerAccountManagement $customerAccountManagement
    	 * @param SubscriptionManagerInterface $subscriptionManager
    	 */
    	public function __construct(
    		Context $context,
    		SubscriberFactory $subscriberFactory,
    		Session $customerSession,
    		StoreManagerInterface $storeManager,
    		CustomerUrl $customerUrl,
    		CustomerAccountManagement $customerAccountManagement,
    		SubscriptionManagerInterface $subscriptionManager
    	) {
    
    		$this->subscriptionManager = $subscriptionManager;
    
    		parent::__construct(
    			$context,
    			$subscriberFactory,
    			$customerSession,
    			$storeManager,
    			$customerUrl,
    			$customerAccountManagement,
    			$subscriptionManager
    		);
    	}
    
    	/**
    	 * New subscription action
    	 *
    	 * @return Redirect
    	 */
    	public function execute() {
    
    		if ($this->getRequest()->isPost() && $this->getRequest()->getPost('email')) {
    
    			$email = (string) $this->getRequest()->getPost('email');
    			$name = (string) $this->getRequest()->getPost('name');
    
    			try {
    
    				$this->validateEmailFormat($email);
    				$this->validateGuestSubscription();
    				$this->validateEmailAvailable($email);
    
    				$websiteId = (int) $this->_storeManager->getStore()->getWebsiteId();
    				/** @var Subscriber $subscriber */
    				$subscriber = $this->_subscriberFactory->create()->loadBySubscriberEmail($email, $websiteId);
    				if ($subscriber->getId()
    					&& (int) $subscriber->getSubscriberStatus() === Subscriber::STATUS_SUBSCRIBED) {
    					throw new LocalizedException(
    						__('This email address is already subscribed.')
    					);
    				}
    
    				$storeId = (int) $this->_storeManager->getStore()->getId();
    				$currentCustomerId = $this->getSessionCustomerId($email);
    				$subscriber = $currentCustomerId
    				? $this->subscriptionManager->subscribeCustomer($currentCustomerId, $storeId)
    				: $this->subscriptionManager->subscribe($email, $storeId);
    
    				if ($subscriber->getSubscriberId() > 0) {
    					$subscriber = $this->_subscriberFactory->create()->loadBySubscriberEmail($email, $websiteId);
    					$subscriber->setFullName($name)->save();
    				}
    
    				$message = $this->getSuccessMessage((int) $subscriber->getSubscriberStatus());
    				$this->messageManager->addSuccessMessage($message);
    			} catch (LocalizedException $e) {
    				$this->messageManager->addComplexErrorMessage(
    					'localizedSubscriptionErrorMessage',
    					['message' => $e->getMessage()]
    				);
    			} catch (Exception $e) {
    				$this->messageManager->addExceptionMessage($e, __('Something went wrong with the subscription.'));
    			}
    		}
    		/** @var Redirect $redirect */
    		$redirect = $this->resultFactory->create(ResultFactory::TYPE_REDIRECT);
    		$redirectUrl = $this->_redirect->getRedirectUrl();
    		return $redirect->setUrl($redirectUrl);
    	}
    
    	/**
    	 * Get customer id from session if he is owner of the email
    	 *
    	 * @param string $email
    	 * @return int|null
    	 */
    	private function getSessionCustomerId(string $email):  ? int {
    		if (!$this->_customerSession->isLoggedIn()) {
    			return null;
    		}
    
    		$customer = $this->_customerSession->getCustomerDataObject();
    		if ($customer->getEmail() !== $email) {
    			return null;
    		}
    
    		return (int) $this->_customerSession->getId();
    	}
    
    	/**
    	 * Get success message
    	 *
    	 * @param int $status
    	 * @return Phrase
    	 */
    	private function getSuccessMessage(int $status) : Phrase {
    
    		if ($status === Subscriber::STATUS_NOT_ACTIVE) {
    
    			return __('The confirmation request has been sent.');
    		}
    
    		return __('Thank you for your subscription.');
    	}
    
    }
    

    Magemonkeys/Newsletter/view/adminhtml/layout/newsletter_subscriber_block.xml

    <?xml version="1.0"?>
    <page xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:View/Layout/etc/page_configuration.xsd">
      <body>
        <referenceBlock name="adminhtml.newslettrer.subscriber.grid.columnSet">
          <block class="MagentoBackendBlockWidgetGridColumn" name="adminhtml.newslettrer.subscriber.grid.columnSet.full.name" as="full.name">
            <arguments>
              <argument name="header" xsi:type="string" translate="true">Name</argument>
              <argument name="index" xsi:type="string">full_name</argument>
              <argument name="header_css_class" xsi:type="string">col-name</argument>
              <argument name="column_css_class" xsi:type="string">ccol-name</argument>
            </arguments>
          </block>
        </referenceBlock>
      </body>
    </page>

    Magemonkeys/Newsletter/view/frontend/templates/subscribe.phtml

    <?php
    /** @var MagentoNewsletterBlockSubscribe $block */
    ?>
    <div class="block newsletter">
      <div class="title"><strong><?php /* @escapeNotVerified */ echo __('Newsletter') ?></strong></div>
      <div class="content">
        <form class="form subscribe"
              novalidate
              action="<?php echo $block->escapeUrl($block->getFormActionUrl()) ?>"
              method="post"
              data-mage-init='{"validation": {"errorClass": "mage-error"}}'
              id="newsletter-validate-detail">
          <div class="field full_name">
            <label class="label" for="full_name"><span><?php echo $block->escapeHtml(__('Name')) ?></span></label>
            <div class="control">
              <input name="full_name" type="text" id="full_name"
                     placeholder="<?php echo $block->escapeHtmlAttr(__('Name')) ?>"
                     data-validate="{required:true}"/>
            </div>
          </div>
          <div class="actions">
            <button class="action subscribe primary" title="<?php echo $block->escapeHtmlAttr(__('Subscribe')) ?>" type="submit">
              <span><?php echo $block->escapeHtml(__('Subscribe')) ?></span>
            </button>
          </div>
        </form>
      </div>
    </div>

    Result :