Showing results for 
Search instead for 
Did you mean: 

Customer E-mail notifications are hard to hook into.

0 Kudos

Customer E-mail notifications are hard to hook into.

Magento 2.1.3:


I've been given the task that when a customer with a certain property registers itself it should get a different e-mail template. What this property is, is not important for the question, but lets say for sake of simplicity I have a Service Contract that can check if the customer qualifies for the different e-mail template or not:


$this->customerChecker->hasCertainProperty($customerId); // returns true or false

Now this might seem like an easy task right? Just hook into `Magento\Customer\Model\EmailNotification` with a plugin or something, and modify the part where the correct e-mail template is selected. Right?


    public function newAccount(
        CustomerInterface $customer,
        $type = self::NEW_ACCOUNT_EMAIL_REGISTERED,
        $backUrl = '',
        $storeId = 0,
        $sendemailStoreId = null
    ) {
        $types = $this->getTemplateTypes();

        if (!isset($types[$type])) {
            throw new LocalizedException(__('Please correct the transactional account email type.'));

        if (!$storeId) {
            $storeId = $this->getWebsiteStoreId($customer, $sendemailStoreId);

        $store = $this->storeManager->getStore($customer->getStoreId());

        $customerEmailData = $this->getFullCustomerObject($customer);

            ['customer' => $customerEmailData, 'back_url' => $backUrl, 'store' => $store],

Right... the e-mail template is sent in this method using sendEmailTemplate(). So we can't use a interceptor for this... Well let's just look at the sendEmailTemplate()-method then:


    private function sendEmailTemplate(
        $templateParams = [],
        $storeId = null,
        $email = null
    ) {
        $templateId = $this->scopeConfig->getValue($template, 'store', $storeId);
        if ($email === null) {
            $email = $customer->getEmail();

        $transport = $this->transportBuilder->setTemplateIdentifier($templateId)
            ->setTemplateOptions(['area' => 'frontend', 'store' => $storeId])
            ->setFrom($this->scopeConfig->getValue($sender, 'store', $storeId))
            ->addTo($email, $this->customerViewHelper->getCustomerName($customer))


Darn! The method is private! So an interceptor will definitely not work here. And we also cannot use a rewrite, since private methods are not inherited. 


The only way to manipulate our desired functionality is by rewriting the EmailNotification and copy/paste everything that is private from this class. Which are a lot of methods and properties.




I would suggest that the EmailNotification-class gets some refactoring so it makes it's easier for 3rd party modules to extend it's functionality. Or am I missing something here?