¿Cómo agregar un cliente mediante programación en Magento 2?


13

Necesito crear un cliente mediante programación en Magento 2, no he encontrado mucha documentación ... básicamente, lo que tengo que hacer es traducir el siguiente código a "Magento 2":

$websiteId = Mage::app()->getWebsite()->getId();
$store = Mage::app()->getStore();

$customer = Mage::getModel("customer/customer");
$customer   ->setWebsiteId($websiteId)
            ->setStore($store)
            ->setFirstname('John')
            ->setLastname('Doe')
            ->setEmail('jd1@ex.com')
            ->setPassword('somepassword');

try{
    $customer->save();
}

¿Quieres hacer esto en un script independiente o tienes un modelo o algo?
Marius

@ Mario, he estado trabajando en este módulo y he creado un controlador. En este controlador, necesito preparar algunos datos para guardarlos y la idea es llamar al modelo del cliente y guardar esa información. El código anterior se puede colocar en un controlador. Me gustaría hacer lo mismo, pero para Magento 2. Todavía estoy un poco confundido con la nueva estructura de Magento 2 y estoy atrapado aquí ahora. Sé que tiene algo que ver con las inyecciones de clase. e instancias de objetos pero no estoy seguro de cómo hacerlo ...
Eduardo

Respuestas:


20

Bien, después de un tiempo encontré una solución en caso de que alguien más la necesitara. Magento usa otro enfoque para crear instancias de objetos, la forma tradicional de crear instancias de objetos en Magento 1.x fue usando "Mage :: getModel (..)", esto han cambiado en Magento 2. Ahora Magento usa un administrador de objetos para instanciar objetos, no ingresaré detalles sobre cómo funciona ... así, el código equivalente para crear clientes en Magento 2 se vería así:

<?php

namespace ModuleNamespace\Module_Name\Controller\Index;

class Index extends \Magento\Framework\App\Action\Action
{
    /**
     * @var \Magento\Store\Model\StoreManagerInterface
     */
    protected $storeManager;

    /**
     * @var \Magento\Customer\Model\CustomerFactory
     */
    protected $customerFactory;

    /**
     * @param \Magento\Framework\App\Action\Context      $context
     * @param \Magento\Store\Model\StoreManagerInterface $storeManager
     * @param \Magento\Customer\Model\CustomerFactory    $customerFactory
     */
    public function __construct(
        \Magento\Framework\App\Action\Context $context,
        \Magento\Store\Model\StoreManagerInterface $storeManager,
        \Magento\Customer\Model\CustomerFactory $customerFactory
    ) {
        $this->storeManager     = $storeManager;
        $this->customerFactory  = $customerFactory;

        parent::__construct($context);
    }

    public function execute()
    {
        // Get Website ID
        $websiteId  = $this->storeManager->getWebsite()->getWebsiteId();

        // Instantiate object (this is the most important part)
        $customer   = $this->customerFactory->create();
        $customer->setWebsiteId($websiteId);

        // Preparing data for new customer
        $customer->setEmail("email@domain.com"); 
        $customer->setFirstname("First Name");
        $customer->setLastname("Last name");
        $customer->setPassword("password");

        // Save data
        $customer->save();
        $customer->sendNewAccountEmail();
    }
}

Espero que este fragmento de código ayude a alguien más ...


66
Estabas muy cerca. Debe evitar usar objectManager directamente siempre que sea posible; es una forma incorrecta. La forma correcta de hacerlo es usar la inyección de dependencia para obtener la clase 'factory' y usarla para crear una instancia. Si no existe una clase de fábrica para una clase determinada, se generará automáticamente. Edité su código para usar esto (agregué la fábrica al constructor y la clase, y llamé a create ()), y sigo los estándares de código PSR-2.
Ryan Hoerr

Gracias por la corrección @RyanH. Pensé en usar clases de fábrica pero no estaba seguro de cómo hacerlo, así que usé objectManager ... Leeré más sobre los estándares de código PSR-2 para futuros proyectos. Estoy usando el código con sus correcciones ahora y todo funciona perfectamente. Gracias
Eduardo

@RyanH. Hecho ; )
Eduardo

Puedo verlo en bases de datos, pero no en el panel de administración. Que pasa
Arni

1
@Arni; mi primera suposición es que necesitarías reindexar :)
Alex Timmer

4

Aquí hay una manera simple de crear un nuevo cliente con el grupo predeterminado y la tienda actual.

use Magento\Framework\App\RequestFactory;
use Magento\Customer\Model\CustomerExtractor;
use Magento\Customer\Api\AccountManagementInterface;

class CreateCustomer extends \Magento\Framework\App\Action\Action
{
    /**
     * @var RequestFactory
     */
    protected $requestFactory;

    /**
     * @var CustomerExtractor
     */
    protected $customerExtractor;

    /**
     * @var AccountManagementInterface
     */
    protected $customerAccountManagement;

    /**
     * @param \Magento\Framework\App\Action\Context $context
     * @param RequestFactory $requestFactory
     * @param CustomerExtractor $customerExtractor
     * @param AccountManagementInterface $customerAccountManagement
     */
    public function __construct(
        \Magento\Framework\App\Action\Context $context,
        RequestFactory $requestFactory,
        CustomerExtractor $customerExtractor,
        AccountManagementInterface $customerAccountManagement
    ) {
        $this->requestFactory = $requestFactory;
        $this->customerExtractor = $customerExtractor;
        $this->customerAccountManagement = $customerAccountManagement;
        parent::__construct($context);
    }

    /**
     * Retrieve sources
     *
     * @return array
     */
    public function execute()
    {
        $customerData = [
            'firstname' => 'First Name',
            'lastname' => 'Last Name',
            'email' => 'customer@email.com',
        ];

        $password = 'MyPass123'; //set null to auto-generate

        $request = $this->requestFactory->create();
        $request->setParams($customerData);

        try {
            $customer = $this->customerExtractor->extract('customer_account_create', $request);
            $customer = $this->customerAccountManagement->createAccount($customer, $password);
        } catch (\Exception $e) {
            //exception logic
        }
    }
}

¿Qué es $ request aquí ?, ¿podemos agregar atributos personalizados también?
jafar pinjar

¿Cómo establecer atributos personalizados?
jafar pinjar

0

Este código se ejecuta en un archivo externo o en un archivo de consola CLI Magento

namespace Company\Module\Console;

use Braintree\Exception;
use Symfony\Component\Console\Command\Command;
use Symfony\Component\Console\Input\InputInterface;
use Symfony\Component\Console\Output\OutputInterface;
use Magento\Framework\App\Bootstrap;


class ImportProducts extends Command
{

    public function magentoStart()
    {
        $startMagento = $this->bootstrap();
        $state = $startMagento['objectManager']->get('Magento\Framework\App\State');
        $state->setAreaCode('frontend');
        return $startMagento['objectManager'];
    }

    protected function bootstrap()
    {
        require '/var/www/html/app/bootstrap.php';
        $bootstrap = Bootstrap::create(BP, $_SERVER);
        $objectManager = $bootstrap->getObjectManager();
        return array('bootstrap' => $bootstrap, 'objectManager' => $objectManager);
    }

    protected function createCustomers($item)
    {
        $objectManager      = $this->magentoStart();
        $storeManager       = $objectManager->create('Magento\Store\Model\StoreManagerInterface');
        $customerFactory    = $objectManager->create('Magento\Customer\Model\CustomerFactory');

        $websiteId  = $storeManager->getWebsite()->getWebsiteId();
        $customer   = $customerFactory->create();
        $customer->setWebsiteId($websiteId);
        $customer->setEmail("eu@mailinator.com");
        $customer->setFirstname("First Name");
        $customer->setLastname("Last name");
        $customer->setPassword("password");
        $customer->save();
    }
}

0

Todos los ejemplos anteriores funcionarán, pero la forma estándar siempre debe ser el uso de contratos de servicio que las clases concretas.

Por lo tanto, se deben preferir las siguientes formas para crear el cliente mediante programación.

                /** @var \Magento\Customer\Api\Data\CustomerInterface $customer */
                $customer = $this->customerFactory->create();
                $customer->setStoreId($store->getStoreId());
                $customer->setWebsiteId($store->getWebsiteId());
                $customer->setEmail($email);
                $customer->setFirstname($firstName);
                $customer->setLastname($lastName);

                /** @var \Magento\Customer\Api\CustomerRepositoryInterface $customerRepository*/
                $customerRepository->save($customer);
Al usar nuestro sitio, usted reconoce que ha leído y comprende nuestra Política de Cookies y Política de Privacidad.
Licensed under cc by-sa 3.0 with attribution required.