1

I have created a custom attribute for customer address. I can see the attribute on admin, I can insert value on frontend, the value saved successfully (and it displayed in address preview) however if I try to edit the address, no value appears.

This is my code. I will appreciate any help.

Sandy\AddressCustomAttributes\Block\Customer\Address\Form\Edit\Comment.php

<?php

namespace Sandy\AddressCustomAttributes\Block\Customer\Address\Form\Edit;

use Magento\Customer\Api\AddressRepositoryInterface;
use Magento\Customer\Api\Data\AddressInterface;
use Magento\Framework\Exception\NoSuchEntityException;
use Magento\Framework\View\Element\Template;
use Magento\Customer\Api\Data\AddressInterfaceFactory;
use Magento\Customer\Model\Session;
use Magento\Framework\View\Element\Template\Context;

class Comment extends Template
{
    /** @var AddressInterface */
    private $address;
    /** @var AddressRepositoryInterface */
    private $addressRepository;
    /** @var AddressInterfaceFactory */
    private $addressFactory;
    /** @var Session */
    private $customerSession;

    /**
     * Comment Constructor
     * @param Template|Context $context
     * @param AddressRepositoryInterface $addressRepository
     * @param AddressInterfaceFactory $addressFactory
     * @param Session $session
     * @param array $data
     */
    public function __construct(
        Context $context,
        AddressRepositoryInterface $addressRepository,
        AddressInterfaceFactory $addressFactory,
        Session $session,
        array $data = []
    )
    {
        parent::__construct($context, $data);
        $this->addressRepository = $addressRepository;
        $this->addressFactory = $addressFactory;
        $this->customerSession = $session;
    }


    protected function _prepareLayout()
    {
        $addressId = $this->getRequest()->getParam('id');

        if ($addressId) {
            try {
                $this->address = $this->addressRepository->getById($addressId);
                if ($this->address->getCustomerId() != $this->customerSession->getCustomerId())
                    $this->address = null;
            } catch (NoSuchEntityException $exception) {
                $this->address = null;
            }
        }
        if (null === $this->address)
            $this->address = $this->addressFactory->create();

        return parent::_prepareLayout();
    }

    /**
     * @return string
     * @throws \Magento\Framework\Exception\LocalizedException
     */
    protected function _toHtml()
    {

        $customWidgetBlock = $this->getLayout()->createBlock(
            'Sandy\AddressCustomAttributes\Block\Customer\Widget\Comment'
        );

        $customWidgetBlock->setAddress($this->address);

        return $customWidgetBlock->toHtml();
    }
}

Sandy\AddressCustomAttributes\Block\Customer\Widget\Comment.php

<?php

namespace Sandy\AddressCustomAttributes\Block\Customer\Widget;

use Magento\Customer\Api\AddressMetadataInterface;
use Magento\Customer\Api\Data\AddressInterface;
use Magento\Framework\View\Element\Template;
use Magento\Framework\Exception\NoSuchEntityException;
use Magento\Framework\Phrase;
use Magento\Framework\View\Element\Template\Context;

class Comment extends Template
{
    /** @var AddressMetadataInterface  */
    private $addressMetadata;

    protected function _construct()
    {
        parent::_construct();
        $this->setTemplate('widget/comment.phtml');
    }

    /**
     * Comment constructor.
     * @param Context $context
     * @param AddressMetadataInterface $addressMetadata
     * @param array $data
     */
    public function __construct(
        Context $context,
        AddressMetadataInterface $addressMetadata,
        array $data = []
    )
    {
        parent::__construct($context, $data);
        $this->addressMetadata = $addressMetadata;
    }


    /**
     * @return bool
     */
    public function isRequired()
    {
        return $this->getAttribute()
            ? $this->getAttribute()->isRequired()
            : false;
    }

    /**
     * @return string
     */
    public function getFieldId()
    {
        return 'comment';
    }

    /**
     * @return Phrase|string
     */
    public function getFieldLabel()
    {
        return $this->getAttribute()
            ? $this->getAttribute()->getFrontendLabel()
            : __('Comment');
    }

    /**
     * @return string
     */
    public function getFieldName()
    {
        return 'comment';
    }

    public function getSortOrder()
    {
        return $this->getAttribute()->getSortOrder();
    }

    /**
     * @return string|null
     */
    public function getValue()
    {
        /** @var AddressInterface $address */
        $address = $this->getAddress();
        if ($address instanceof AddressInterface) {
            return $address->getCustomAttribute('comment')
                ? $address->getCustomAttribute('comment')->getValue()
                : null;
        }
        return null;
    }

    private function getAttribute()
    {
        try {
            $attribute = $this->addressMetadata->getAttributeMetadata('comment');
        } catch (NoSuchEntityException $exception) {
            $attribute = null;
        }

        return $attribute;
    }
}

Sandy\AddressCustomAttributes\Plugin\Customer\AddressEditPlugin.php

<?php

namespace Sandy\AddressCustomAttributes\Plugin\Customer;

use Magento\Framework\View\LayoutInterface;

class AddressEditPlugin
{

    /** @var LayoutInterface */
    private $layout;

    public function __construct(
        LayoutInterface $layout
    )
    {
        $this->layout = $layout;
    }

    /**
     * @param \Magento\Customer\Block\Address\Edit $edit
     * @param $result
     * @return string
     */
    public function afterGetNameBlockHtml(
        \Magento\Customer\Block\Address\Edit $edit,
        $result
    )
    {
        $customBlock = $this->layout->createBlock(
            'Sandy\AddressCustomAttributes\Block\Customer\Address\Form\Edit\Comment',
            'sandy_address_custom_attributes_comment'
        );

        return $result . $customBlock->toHtml();
    }
}

view/frontend/templates/widget/comment.phtml

<?php /** @var \Sandy\AddressCustomAttributes\Block\Customer\Widget\Comment $block */ ?>
<div class="field comment <?php if($block->isRequired()) echo ' required'; echo $block->escapeHtml($block->getSortOrder());?>">
    <label class="label" for="<?php echo $block->escapeHtml($block->getFieldId()); ?>">
        <span>
            <?php echo $block->escapeHtml($block->getFieldLabel()); ?>
        </span>
    </label>
    <div class="control">
        <input type="text"
            id="<?php echo $block->escapeHtml($block->getFieldId()); ?>"
            name="<?php echo $block->escapeHtml($block->getFieldName()); ?>"
            value="<?php echo $block->escapeHtml($block->getValue()); ?>"
            title="<?php echo $block->escapeHtml($block->getFieldLabel()); ?>"
            class="input-text"
            <?php /* @escapeNotVerified */ echo $block->escapeHtml($block->getFieldParams()); ?>
            <?php if($block->isRequired()) echo 'data-validate="{required:true}"' ?> 
        />
    </div>
</div>

Sandy\AddressCustomAttributes\Setup\InstallData

<?php


namespace Sandy\AddressCustomAttributes\Setup;

use Magento\Framework\Setup\InstallDataInterface;
use Magento\Framework\Setup\ModuleDataSetupInterface;
use Magento\Customer\Model\Customer;
use Magento\Framework\Setup\ModuleContextInterface;
use Magento\Customer\Setup\CustomerSetupFactory;

class InstallData implements InstallDataInterface
{

    private $customerSetupFactory;

    /**
     * Constructor
     *
     * @param \Magento\Customer\Setup\CustomerSetupFactory $customerSetupFactory
     */
    public function __construct(
        CustomerSetupFactory $customerSetupFactory
    ) {
        $this->customerSetupFactory = $customerSetupFactory;
    }

    /**
     * {@inheritdoc}
     */
    public function install(
        ModuleDataSetupInterface $setup,
        ModuleContextInterface $context
    ) {
        $customerSetup = $this->customerSetupFactory->create(['setup' => $setup]);

        $customerSetup->addAttribute(\Magento\Customer\Model\Indexer\Address\AttributeProvider::ENTITY, 'comment', [
            'label' => 'Comment',
            'input' => 'textarea',
            'type' => 'text',
            'source' => '',
            'required' => false,
            'position' => 1001,
            'visible' => true,
            'system' => false,
            'is_used_in_grid' => false,
            'is_visible_in_grid' => false,
            'is_filterable_in_grid' => false,
            'is_searchable_in_grid' => false,
            'backend' => ''
        ]);


        $attribute = $customerSetup->getEavConfig()->getAttribute('customer_address', 'comment')
            ->addData(['used_in_forms' => [
                'adminhtml_customer_address',
                'customer_address_edit',
                'customer_register_address'
            ]]);
        $attribute->save();
    }
}
0

You have to add this attribute as extension attribute using below code

<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:Api/etc/extension_attributes.xsd">
    <extension_attributes for="Magento\Customer\Api\Data\AddressInterface">
        <attribute code="comment" type="string" />
    </extension_attributes>
</config>

this code, will be written at Sandy\AddressCustomAttributes\etc\extension_attributes.xml

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

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