how can we get the customer data from id not from customer session in Magento2.
Kindly let me know.
You can get all customer data from customer id in Magento 2. Here is the code snippet
<?php
$objectManager = \Magento\Framework\App\ObjectManager::getInstance();
$customerFactory = $objectManager->get('\Magento\Customer\Model\CustomerFactory')-
>create();
$customerId = 1;
$customer = $customerFactory->load($customerId);
//fetch whole customer information
echo "<pre>";
print_r($customer->getData());
//fetch specific information
echo $customer->getEmail();
echo $customer->getFirstName();
echo $customer->getLastName();
You can also get customer billing address and shipping address from customer id. Full post is in this link
For the demonstrated purpose I have used Objectmanager. One should always use constructor method.
Load the customer by using the api factory. This is the correct way.
<?php
namespace Yourcompany\Customer\Helper {
/**
* Eav data helper
*/
class Data extends \Magento\Framework\App\Helper\AbstractHelper
{
protected $customerRepository;
public function __construct(
\Magento\Customer\Api\CustomerRepositoryInterfaceFactory $customerRepositoryFactory) {
$this->customerRepository = $customerRepositoryFactory->create();
}
public function LoadCustomerById($customerId) {
$cst = $this->customerRepository->getById($customerId);
return $cst;
}
}
?>
Here is the code snippet to get customer data by using id programmatically in magento 2 version
use \Magento\Framework\App\Bootstrap;
include('app/bootstrap.php');
$bootstrap = Bootstrap::create(BP, $_SERVER);
$objectManager = $bootstrap->getObjectManager();
$url = \Magento\Framework\App\ObjectManager::getInstance();
$storeManager = $url->get('\Magento\Store\Model\StoreManagerInterface');
$state = $objectManager->get('\Magento\Framework\App\State');
$state->setAreaCode('frontend');
$websiteId = $storeManager->getWebsite()->getWebsiteId();
// Get Store ID
$store = $storeManager->getStore();
$storeId = $store->getStoreId();
$customerFactory = $objectManager->get('\Magento\Customer\Model\CustomerFactory');
$customer=$customerFactory->create();
$customer->setWebsiteId($websiteId);
//$customer->loadByEmail('example#gmail.com');// load customer by email address
//echo $customer->getEntityId();
$customer->load('1');// load customer by using ID
$data= $customer->getData();
print_r($data);
You can get customer data by id by following way
namespace Vendor\Module\Block\Index;
class Index extends \Magento\Framework\View\Element\Template
{
protected $_customer;
public function __construct(
\Magento\Customer\Model\Customer $customer,
\Magento\Backend\Block\Template\Context $context
)
{
$this->_customer = $customer;
parent::__construct($context);
}
public function getCustomer()
{
$customerId = '3'; //You customer ID
$customer = $this->_customer->getCollection()->addAttributeToFilter('entity_id', array('eq' => '3'));
print_r($customer->getData());//Customer data by customer ID
}
}
It is recommended to use dependency injection instead of using object manager.
Create block like
namespace Lapisbard\General\Block;
use Magento\Customer\Model\Session;
class CustomerAccount extends \Magento\Framework\View\Element\Template {
public function __construct(
Session $customerSession,
\Magento\Framework\View\Element\Template\Context $context
)
{
parent::__construct($context);
$this->_customerSession = $customerSession;
}
public function getCustomerName(){
$this->_customerSession->getCustomer()->getName();
}
}
And use it in your template like
<?php echo $block->getCustomerName(); ?>
$objectManager = \Magento\Framework\App\ObjectManager::getInstance();
$customer = $objectManager->create('Magento\Customer\Model\Customer')->load($customerId);
$xxx = $customer->getData('xxx');
$customer = $this->objectManager->create('Magento\Customer\Model\Customer')->load(1);
Instead of objectManager you should use dependency injection.
This is the old Ans Magento updated this
You can get customer data from following method also more options are available
$objectManager = \Magento\Framework\App\ObjectManager::getInstance();
$customer = $objectManager->create('Magento\Customer\Model\Customer')->load(1);
Also you can use Magento\Customer\Model\Customer for blocks using dependency injection.The main benefits of using object manager is it can be used in phtml.
I am facing same problem when Cache enable I am not able to get customer session.But I find below solution
/**
* #var \Magento\Customer\Model\Session
*/
protected $_customerSession;
public function __construct(Template\Context $context,
\Magento\Framework\App\Request\Http $request,
\Magento\Customer\Api\CustomerRepositoryInterface $customerRepository,
\Magento\Customer\Model\SessionFactory $customerSession
)
{
$this->request = $request;
$this->customerRepository = $customerRepository;
$this->_customerSession = $customerSession;
parent::__construct($context);
}
public function getCustomerId(){
$customer = $this->_customerSession->create();
var_dump($customer->getCustomer()->getId());
}
Use above code in block It is working even cache is enable.
Second Solution:
Add cacheable="false" in your xml
<referenceContainer name="content">
<block class="Vendor\Modulename\Block\Customer" name="customer.session.data" template="Vendor_Modulename::customertab.phtml" cacheable="false" />
</referenceContainer>
Add below code in block:
/**
* #var \Magento\Customer\Model\Session
*/
protected $_customerSession;
/**
* Construct
*
* #param \Magento\Framework\View\Element\Template\Context $context
*/
public function __construct(Template\Context $context,
\Magento\Framework\App\Request\Http $request,
\Magento\Customer\Api\CustomerRepositoryInterface $customerRepository,
\Magento\Customer\Model\Session $customerSession
)
{
$this->request = $request;
$this->customerRepository = $customerRepository;
$this->_customerSession = $customerSession;
parent::__construct($context);
}
public function getOrderData(){
$customerId = $this->_customerSession->getCustomerId();
var_dump($this->_customerSession->getCustomer());
}
Get Customer Details In Magento2 By Id
use Magento\Customer\Model\CustomerFactory;
class CustomClass {
/**
* #var CustomerFactory
*/
private $customerFactory;
public function __construct(
CustomerFactory $customerFactory,
) {
$this->customerFactory = $customerFactory;
}
public function getCustomerDetails() {
$customerId=6;
// $customerId =$this->getCustomerIdByEmail();
// $customerId =$this->getCustomerIdByMobile();
$loadData =$this->customerFactory->create()->load($customerId);
$allData = $loadData->getData());
print_r($allData);
}
}
To Get The Customer ID By Email
public function getCustomerIdByEmail() {
$customerId = $this->customerFactory->create()->getCollection()
->addFieldToFilter('email', $email)
->getFirstItem()->getId();
}
To Get The Customer ID By Mobile Number
public function getCustomerIdByMobile() {
$customerId = $this->customerFactory->create()->getCollection()
->addFieldToFilter('mobile_number', $mobile_number)
->getFirstItem()->getId();
}
Related
I want customer SessionID along with customer ID.
public function __construct
(
\Magento\Framework\Session\SessionManager $sessionManager
)
{
$this->_session = $sessionManager;
}
public function execute(\Magento\Framework\Event\Observer $observer)
{
$sessionID = $this->_session->getSessionId();
}
I have created form which requires data transformer, but got myself into single problem: I transform data by exploding string (string should be be exploded to 3 parts), everything works, if I supply correct format string, but otherwise it throws error inside data transformer, because transformation cannot occur if wrong string format is supplied (this is expected behavior).
So the question is is there a way to validate form field for correct string before data transformation? I know that data transformation by default occurs before validation, but maybe there's a way to do it other way around?
I found one solution that might work on this thread: Combine constraints and data transformers ,
but it's looks like rough solution, besides I need to translate validation message, and I would really like to do it using default translation methods for symfony forms (without using translation service)
I thought, and also someone from symfony IRC (Iltar) suggested do it by using events, but I'm not sure how to go about this - how to attach data transformer dynamically to form field? Or maybe there's other way?
It's maybe too late but I eventually manage to do it.
Maybe it will help you.
Here is my FormType:
class PersonType extends AbstractType{
public function buildForm(FormBuilderInterface $builder, array $options){
$builder->add('mother', 'personSelector', array('personEntity' => $options['personEntity']));
}
}
Here is my customField where are validations:
class PersonSelectorType extends AbstractType{
public function buildForm(FormBuilderInterface $builder, array $options){
$transformer = new PersonByFirstnameAndLastnameTransformer($this->entityManager,$options);
$builder->addModelTransformer($transformer);
$builder->addEventListener(FormEvents::PRE_SUBMIT, array($this, 'onPreSubmitForm'));
}
public function onPreSubmitForm(FormEvent $event){
$mother = $event->getData();
$form = $event->getForm();
$options = $form->getConfig()->getOptions();
if (!empty($mother)){
preg_match('#(.*) (.*)#', $mother, $personInformations);
if (count($personInformations) != 3){
$form->addError(new FormError('[Format incorrect] Le format attendu est "Prénom Nom".'));
}else{
$person = $this->entityManager->getRepository($options['personEntity'])->findOneBy(array('firstname' => $personInformations[1],'lastname' =>$personInformations[2]));
if ($person === null) {
$form->addError(new FormError('Il n\'existe pas de person '.$personInformations[1].' '.$personInformations[2].'.'));
}
}
}
}
}
Here is my transformer:
class PersonByFirstnameAndLastnameTransformer implements DataTransformerInterface{
public function reverseTransform($firstnameAndLastname) {
if (empty($firstnameAndLastname)) { return null; }
preg_match('#(.*) (.*)#', $firstnameAndLastname, $personInformations);
$person = $this->entityManager->getRepository($this->options['personEntity'])->findOneBy(array('firstname' =>$personInformations[1],'lastname' =>$personInformations[2]));
if (count($personInformations) == 3){
$person = $this->entityManager->getRepository($this->options['personEntity'])->findOneBy(array('firstname' =>$personInformations[1],'lastname' =>$personInformations[2]));
}
return $person;
}
public function transform($person) {
if ($person === null) { return ''; }
return $person->getFirstname().' '.$person->getLastname();
}
}
Perhaps you could pass the instance of your form to your transformer. If the string doesn't parse correctly, simply add a validation error to the form, like so:
<?php
// src/Acme/MyBundle/Form/DataTransformer/StringTransformer.php
namespace Acme\MyBundle\Form\DataTransformer;
use Symfony\Component\Form\DataTransformerInterface;
use Symfony\Component\Form\Exception\TransformationFailedException;
use Doctrine\Common\Persistence\ObjectManager;
use Acme\MyBundle\Entity\MyEntity;
use Acme\MyBundle\Entity\AnotherEntity;
use Acme\MyBundle\Type\MyEntityType;
class StringTransformer implements DataTransformerInterface
{
/**
* #var MyEntityType
*/
private $form;
/**
* #param ObjectManager $om
*/
public function __construct(MyEntityType $form)
{
$this->form = $form;
}
/**
* Transforms an object (entity) to a string (number).
*
* #param MyEntity|null $entity
* #return string
*/
public function transform($value)
{
// ...
}
/**
* Transforms a string (number) to an object (entity).
*
* #param string $number
*
* #return MyEntity|null
*
* #throws TransformationFailedException if object (entity) is not found.
*/
public function reverseTransform($value)
{
$collection = new ArrayCollection();
try{
$vals = explode(',', $value);
foreach($vals as $v){
$entity = new AnotherEntity();
$entity->setValue($v);
$collection->add($v);
}
} catch(\Exception $e){
$this->form
->get('my_location')
->addError(new FormError('error message'));
}
return $collection;
}
}
but it's looks like rough solution, besides I need to translate validation message, and I would really like to do it using default translation methods for symfony forms (without using translation service)
I know this question is old, but as any answer has been marked yet as the right solution, I share with you another approach.
emottet solution, using a presubmit listener to validate the data before the model transformer has been applied, is a good approach, based on this discussion.
If you want to keep using Symfony validation system for these errors too, you could use Symfony validator service (ValidatorInterface) in your pre-submit listener and pass it the required constraints, for example:
$builder
->add('whatever1', TextType::class)
->add('whatever2', TextType::class)
;
$builder->get('whatever1')
->addEventListener(FormEvents::PRE_SUBMIT, function(FormEvent $event) {
$data = $event->getData();
$form = $event->getForm();
/** #var ConstraintViolationListInterface $errors */
if ($errors = $this->validator->validate($data, new Choice([
'choices' => $allowedChoices,
'message' => 'message.in.validators.locale.xlf'
]))) {
/** #var ConstraintViolationInterface $error */
foreach ($errors as $error) {
$form->addError(new FormError($error->getMessage()));
}
}
})
->addModelTransformer($myTransformer)
;
Kind of redundant, but it works. More info here.
Im am new in Zend Framework.
I have this structure of codes .
DBTable
class Application_Model_DbTable_Employee extends Zend_Db_Table_Abstract
{
protected $_name = 'tab_employee';
}
Model
public function selectAllEmployees(){
$tblEmployee = new Application_Model_DbTable_Employee();
$tblEmployee->select('*');
}
But i can can't get all the data of all the employee .
public function selectAllEmployees(){
$tblEmployee = new Application_Model_DbTable_Employee();
return $tblEmployee->fetchAll($tblEmployee->select());
}
Try this code in model:
public function selectAllEmployees(){
$tblEmployee = new Application_Model_DbTable_Employee();
$rowset = $tblEmployee->fetchAll();
return $rowset;
}
For further information read this http://framework.zend.com/manual/1.12/en/zend.db.table.rowset.html#zend.db.table.rowset.to-array
Model function
public function selectAllEmployees()
{
$selectSql = $this->select();
$selectSql->from($this->_name, array('*'))
->order(id DESC');
return $this->fetchAll($selectSql);
}
in the controller
$employeeModel = new Application_Model_Employee();
$employees = $employeeModel->selectAllEmployees();
Maks3w is correct as well as terse.
Here is a little more detail.
There are a number of ways to use your Application_Model_DbTable_Employee to access and query your tab_employee table of your database.
The easiest way is to query directly from the dbTable model itself:
class Application_Model_DbTable_Employee extends Zend_Db_Table_Abstract
{
protected $_name = 'tab_employee';
public function selectAllEmployees()
{
//$this refers to the current dbTable object
$select = $this->select();
//when querying from the dbTable the from() parameter is assumed to be $this->_name, array('*')
//there several other sql commands available to the select(), where(), orWhere(), join()
$select->order('id DESC');
$result = $this->fetchAll($select);
return $result;
}
}
Controller code:
public function indexAction(){
model = new Application_Model_DbTable_Employee();
$employees = $model->selectAllEmployees();
$this->view->employees = $employees
}
Often a mapper model is used to access the database and provide the data to an entity model. This is also very common a relatively simple to accomplish. The key item to remember when designing the mapper is to include code to access the dbTable model as the database adapter, often called the gateway, here is some example code:
<?php
//This is one way to build a mapper
abstract class My_Model_Mapper_Abstract
{
/**
* Instance of Zend_Db_Table_Abstract
*/
protected $tableGateway = null;
/**
* Will accept a DbTable model passed or will instantiate
* a Zend_Db_Table_Abstract object from table name.
*/
public function __construct(Zend_Db_Table_Abstract $tableGateway = null)
{
if (is_null($tableGateway)) {
$this->tableGateway = new Zend_Db_Table($this->_tableName);
} else {
$this->tableGateway = $tableGateway;
}
}
/**
* Get default database table adapter
*/
protected function getGateway()
{
return $this->tableGateway;
}
/**
* findAll() is a proxy for the fetchAll() method and returns
* an array of entity objects.
*
* #param $where, primary key id
* #param string $order in the format of 'column ASC'
* #return array of entity objects
*/
public function findAll($where = null, $order = null)
{
$select = $this->getGateway()->select();
if (!is_null($where)) {
$select->where('id = ?', $where);
}
if (!is_null($order)) {
$select->order($order);
}
$rowset = $this->getGateway()->fetchAll($select);
$entities = array();
foreach ($rowset as $row) {
$entity = $this->createEntity($row);
$this->setMap($row->id, $entity);
$entities[] = $entity;
}
return $entities;
}
/**
* Abstract method to be implemented by concrete mappers.
*/
abstract protected function createEntity($row);
}
The concrete model might look like:
<?php
class Application_Model_Mapper_Employee extends My_Model_Mapper_Abstract
{
protected $tableName = 'tab_employee';
//I hard code the $tableGateway though this is probably not the best way.
//$tableGateway should probably be injected, but I'm lazy.
public function __construct(Zend_Db_Table_Abstract $tableGateway = null)
{
if (is_null($tableGateway)) {
$tableGateway = new Application_Model_DbTable_User();
} else {
$tableGateway = $tableGateway;
}
parent::__construct($tableGateway);
}
//create the Entity model
protected function createEntity($row)
{
$data = array(
'id' => $row->id,
'name' => $row->name,
'password' => $row->password,
);
$employee = new Application_Model_Employee($data);
return $employee;
}
}
to use this in a controller might look like:
public function indexAction(){
model = new Application_Model_Mapper_Employee();
$employees = $model->findAll();
}
and the most direct way to query your database is least recommended way, directly from the controller:
public function indexAction(){
model = new Application_Model_DbTable_Employee();
$employees = $model->fetchAll();
$this->view->employees = $employees
}
I hope this provides you some help and not to much confusion.
I'm using Zend Framework and implementing Domain Model. I have Models, Mappers and DbTables.
Suppose we should fetch multiple rows from database or fetch form data where we should create multiple models and populate that models from database rows or form.
Should I implement fetching and creation of models in Mapper and then call that method from Controller? Or I should implement this in Model?
Is it okay to initialize Mapper in Controller?
The short answer is YES!
If you need to get anything from the database you almost have use the mapper somewhere, because ideally the domain model should not be aware of the database at all or event hat a mapper exists really.
There are I'm sure many strategies and patterns for using and accessing domain models and mappers. I'm also sure that everyone will have differing opinions on how best to utilize these resources. The bottom line is that you have to use what you know how to use, you can always refactor later when you know more.
Just by way of example I'll include a base mapper and a base entity(domain) model.
<?php
/**
* Base mapper model to build concrete data mappers around.
* Includes identity map functionallity.
*/
abstract class My_Application_Model_Mapper
{
protected $_tableGateway = NULL;
protected $_map = array();
/**
* Will accept a DbTable model passed or will instantiate
* a Zend_Db_Table_Abstract object from table name.
*
* #param Zend_Db_Table_Abstract $tableGateway
*/
public function __construct(Zend_Db_Table_Abstract $tableGateway = NULL) {
if (is_null($tableGateway)) {
$this->_tableGateway = new Zend_Db_Table($this->_tableName);
} else {
$this->_tableGateway = $tableGateway;
}
}
/**
* #return Zend_Db_Table_Abstract
*/
protected function _getGateway() {
return $this->_tableGateway;
}
/**
* #param string $id
* #param object $entity
*/
protected function _setMap($id, $entity) {
$this->_map[$id] = $entity;
}
/**
* #param string $id
* #return string
*/
protected function _getMap($id) {
if (array_key_exists($id, $this->_map)) {
return $this->_map[$id];
}
}
/**
* findByColumn() returns an array of rows selected
* by column name and column value.
* Optional orderBy value.
*
* #param string $column
* #param string $value
* #param string $order
* #return array
*/
public function findByColumn($column, $value, $order = NULL) {
$select = $this->_getGateway()->select();
$select->where("$column = ?", $value);
if (!is_null($order)) {
$select->order($order);
}
$result = $this->_getGateway()->fetchAll($select);
$entities = array();
foreach ($result as $row) {
$entity = $this->createEntity($row);
$this->_setMap($row->id, $entity);
$entities[] = $entity;
}
return $entities;
}
/**
* findById() is proxy for find() method and returns
* an entity object. Utilizes fetchRow() because it returns row object
* instead of primary key as find() does.
* #param string $id
* #return object
*/
public function findById($id) {
//return identity map entry if present
if ($this->_getMap($id)) {
return $this->_getMap($id);
}
$select = $this->_getGateway()->select();
$select->where('id = ?', $id);
//result set, fetchRow returns a single row object
$row = $this->_getGateway()->fetchRow($select);
//create object
$entity = $this->createEntity($row);
//assign object to odentity map
$this->_setMap($row->id, $entity);
return $entity;
}
/**
* findAll() is a proxy for the fetchAll() method and returns
* an array of entity objects.
* Optional Order parameter. Pass order as string ie. 'id ASC'
* #param string $order
* #return array
*/
public function findAll($order = NULL) {
$select = $this->_getGateway()->select();
if (!is_null($order)) {
$select->order($order);
}
$rowset = $this->_getGateway()->fetchAll($select);
$entities = array();
foreach ($rowset as $row) {
$entity = $this->createEntity($row);
$this->_setMap($row->id, $entity);
$entities[] = $entity;
}
return $entities;
}
/**
* Abstract method to be implemented by concrete mappers.
*/
abstract protected function createEntity($row);
}
Here is the base domain object:
<?php
/**
* Base domain object
* includes lazy loading of foreign key objects.
*/
abstract class My_Application_Model_Entity_Abstract
{
protected $_references = array();
/**
* Accepts an array to instantiate the object, else use
* __set() when creating objects
* #param array $options
*/
public function __construct(array $options = NULL) {
if (is_array($options)) {
$this->setOptions($options);
}
}
/**
* #param array $options
* #return \My_Application_Model_Entity_Abstract
*/
public function setOptions(array $options) {
$methods = get_class_methods($this);
foreach ($options as $key => $value) {
$method = 'set' . ucfirst($key);
if (in_array($method, $methods)) {
$this->$method($value);
}
}
return $this;
}
/**
* Map the setting of non-existing fields to a mutator when
* possible, otherwise use the matching field
*/
public function __set($name, $value) {
$property = '_' . strtolower($name);
if (!property_exists($this, $property)) {
throw new \InvalidArgumentException("Setting the property '$property'
is not valid for this entity");
}
$mutator = 'set' . ucfirst(strtolower($name));
if (method_exists($this, $mutator) && is_callable(array($this, $mutator))) {
$this->$mutator($value);
} else {
$this->$property = $value;
}
return $this;
}
/**
* Map the getting of non-existing properties to an accessor when
* possible, otherwise use the matching field
*/
public function __get($name) {
$property = '_' . strtolower($name);
if (!property_exists($this, $property)) {
throw new \InvalidArgumentException(
"Getting the property '$property' is not valid for this entity");
}
$accessor = 'get' . ucfirst(strtolower($name));
return (method_exists($this, $accessor) && is_callable(array(
$this, $accessor))) ? $this->$accessor() : $this->$property;
}
/**
* Get the entity fields.
*/
public function toArray() {
//TODO
}
/**
* set and get for _references array, allows the potential to lazy load
* foreign objects.
*/
public function setReferenceId($name, $id) {
$this->_references[$name] = $id;
}
public function getReferenceId($name) {
if (isset($this->_references[$name])) {
return $this->_references[$name];
}
}
}
I have referenced many tutorials and books to finally get my head around these concepts and techniques.
The use of these objects is as needed, if you need to pull an object from the DB you call the mapper, if you need to build an object with form data (or some other data) you can call the object directly.
I hope this helps some. Good Luck!
I use the same architecture and design patterns in all my ZF work. Your mappers should be the only classes in your whole system that access the database. This ensures good Separation of Concerns.
I've toyed a bit with using thin wrapper methods in my Models, such as:
class Application_Model_Foo {
public function save() {
$mapper = $this->_getMapper();
$mapper->save($this);
}
}
This enables me to call something like:
$foo = new Application_Model_Foo();
$foo->setBar('baz-bum');
$foo->save();
But this makes testing more complicated and muddies the water when it comes to SoC. Lately I've been removing such occurrences from my code in favor of just calling up the mapper directly, as in:
$foo = new Application_Model_Foo();
$foo->setBar('baz-bum');
$mapper = new Application_Model_FooMapper();
$mapper->save($foo);
The latter example means one more line of code in my controller method, but for simplicity in testing I think it's worth it.
i am having some problem with zend multidb. My adapters are not getting switched and which ever i sets as default is getting used every time. And also its not giving me any error as well.
Following is the code i am using for zend multidb feature.
Bootstrap.php
public function _initDB()
{
Zend_Registry::getInstance();
$this->bootstrap('multidb');
$multidb = $this->getPluginResource('multidb');
Zend_Registry::set('dbR', $multidb->getDb('dbR'));
Zend_Registry::set('dbW', $multidb->getDb('dbW'));
}
Application.ini
resources.multidb.dbR.adapter = "mysqli"
resources.multidb.dbR.host = "xxx.xxx.x.xx"
resources.multidb.dbR.username = "root"
resources.multidb.dbR.password = "admin"
resources.multidb.dbR.dbname = "test_app1"
resources.multidb.dbR.profiler = "false"
resources.multidb.dbR.isDefaultTableAdapter = "true"
resources.multidb.dbW.adapter = "mysqli"
resources.multidb.dbW.host = "xxx.xxx.x.xx"
resources.multidb.dbW.username = "root"
resources.multidb.dbW.password = "admin"
resources.multidb.dbW.dbname = "test_app2"
Now in my model class i use following line of code where i wants to perform any write operation
class Abc_Model_ModelName extends Zend_Db_Table_Abstract
{
protected $_dbR;
protected $_dbW;
protected $_name = 'table_name';
public function init(){
$this->_dbR = Zend_Registry::get("dbR");
$this->_dbW = Zend_Registry::get("dbW");
}
public function addedit($data = array())
{
$this->setDefaultAdapter($this->_dbW);
}
}
can anyone help me out with this?
I believe you need to call $this->_setAdapter($reader); instead of setDefaultAdapter() function.
_setAdapter will set the new adapter to the existing db table, while setDefaultAdapter() will only set the default adapter that will be used from now on.
Something like:
/**
* Returns an instance of a Zend_Db_Table_Select object.
*
* #param bool $withFromPart Whether or not to include the from part of the select based on the table
* #return Zend_Db_Table_Select
*/
public function slaveSelect($withFromPart = self::SELECT_WITHOUT_FROM_PART)
{
$reader = $this->_getMultiDb()->getRandomReadOnlyAdapter();
$this->_setAdapter($reader);
return parent::select($withFromPart);
}
Looks like you'll either need to pass the db adapter instance in when you call the model in your controller:
public function someAction() {
$db = Zend_Registry::get("dbW");
$model = new Abc_Model_ModelName(array('db'=>$db));
}
or you can override the constructor in your model class:
public function __construct() {
$this->_db = Zend_Registry::get("dbW");
parent::__construct();
}
the database adapter is prepared in the constructor of Zend_Db_Table_Abstract:
/**
* Constructor.
*
* Supported params for $config are:
* - db = user-supplied instance of database connector,
* or key name of registry instance.
* - name = table name.
* - primary = string or array of primary key(s).
* - rowClass = row class name.
* - rowsetClass = rowset class name.
* - referenceMap = array structure to declare relationship
* to parent tables.
* - dependentTables = array of child tables.
* - metadataCache = cache for information from adapter describeTable().
*
* #param mixed $config Array of user-specified config options, or just the Db Adapter.
* #return void
*/
public function __construct($config = array())
{
/**
* Allow a scalar argument to be the Adapter object or Registry key.
*/
if (!is_array($config)) {
$config = array(self::ADAPTER => $config);
}
if ($config) {
$this->setOptions($config);
}
$this->_setup();
$this->init();
}
Hope this helps.