i m doing ZF2 MongoDB ODM authentication but getting the error "An exception was raised while creating "doctrine.documentmanager.odm_default"; no instance returned" and "Drivers must specify a class" i m using the configuration from the ZF2 MongoDB ODM authentication Tutorial
any help would be appreciated, thanks
i have done two things to do it.
1-i have solved it by changing the Drivers path as it was not assigning.
'odm_driver' => array(
'class' => 'Doctrine\ODM\MongoDB\Mapping\Driver\AnnotationDriver',
'paths' => array(__DIR__ . '/../src/' . __NAMESPACE__ . '/Document')
),
'odm_default' => array(
'drivers' => array(
__NAMESPACE__ . '\Document' => 'odm_driver'
)
)
2-then i made two objects of getUsername and getPassword in the user Admin/Document/user
public function getUsername(){
return $this->username;
}
public function getPassword(){
return $this->password;
}
Related
I have several modules in my zf2 application, they all have their own entities and all on the same connection.
A little diagram to explain the situation :
-Module 1
-Entity A
-Entity B
-Module 2
-Entity C
-Entity B
(all on the same database connection)
The problem is all the entities are working, i can fetch, update them, etc. but some are "invisible". I have some cross-module relations and they are working fine too.
For exemple, all entities from module 2 does not appear when I use the php public/index.php orm:info command nor in the Zend Developer Toolbar.
When I edit an entity, I have to manually update the database as php public/index.php orm:schema-tool:update says Nothing to update - your database is already in sync with the current entity metadata.
The entities can be fetched, they are just not "seen" by the ZDT nor the terminal, I don't know what I did wrong.
Thanks for your help
This is often caused when the path to the entities has not been declared in your config:
<?php
return array(
'doctrine' => array(
'driver' => array(
// defines an annotation driver with two paths, and names it `my_annotation_driver`
'my_annotation_driver' => array(
'class' => 'Doctrine\ORM\Mapping\Driver\AnnotationDriver',
'cache' => 'array',
'paths' => array(
'path/to/my/entities',
'another/path'
),
),
// default metadata driver, aggregates all other drivers into a single one.
// Override `orm_default` only if you know what you're doing
'orm_default' => array(
'drivers' => array(
// register `my_annotation_driver` for any entity under namespace `My\Namespace`
'My\Namespace' => 'my_annotation_driver'
)
)
)
)
);
Configuration of doctrine in Zend Framework:
This is the configuration to use mysql driver but i want tu use the PDO database driver for ibase.
<?php
return array(
'doctrine' => array(
'connection' => array(
'orm_default' => array(
'driverClass' => 'Doctrine\DBAL\Driver\PDOMySql\Driver',
'params' => array(
'driver_options' => array(
PDO::MYSQL_ATTR_INIT_COMMAND => 'SET NAMES UTF8'
),
),
),
)
));
?>
Dbal Doctrine driver for firebird is a work in progress not yet merged on github
http://www.doctrine-project.org/jira/browse/DBAL-95
I have requested the patch and it will be integrated soon
On the Zend Framework side it should be possible to use the pdo addapter without dbal (unsupported yet)
https://zf2.readthedocs.org/en/latest/modules/zend.db.adapter.html#zend-db-adapter
Thanks!
Looks like meanwhile i can use the PDO for Ibase with a Zend Adapter
return array(
'db' => array(
'driver' => 'PDO_FIREBIRD',
'database' => 'localhost:C:\Base.FDB',
'username' => 'SYSDBA',
'password' => 'masterkey',
),
);
Well the question pretty much lies in the title. I've read the docs and what I can't find out is how to register the function to my ORM Configuration.
Any help here? Thanks!
Edit: Okay I've done it as Sam said, and made my own class and registered it like
'numeric_functions' => array(
'LOG10' => 'Admin\Model\Log10',
),
However it can't find the class and gives the error
Class 'Admin\Model\Log10' not found in C:\webserver\apache\htdocs\test\vendor\doctrine\orm\lib\Doctrine\ORM\Query\Parser.php on line 3322
Any idea on why this happens?
Actually the link that #foozy gave you is all that you'd need. You simply extend your doctrine configuration array:
return array(
'doctrine' => array(
'connection' => array(
'orm_default' => array(
// Foo
)
),
'configuration' => array(
'orm_default' => array(
'numeric_functions' => array(
'MD5' => 'DoctrineExtensions\Query\Mysql\Md5'
),
'datetime_functions' => array(),
'string_functions' => array(),
'metadata_cache' => 'filesystem',
'query_cache' => 'filesystem',
'result_cache' => 'filesystem',
)
)
)
);
The error is connected to DoctrineExtensions autoload. For me both solutions from How to implement beberlei doctrine extensions in zend framework 2 (manual injection of custom functions and applying via config) worked.
I have a ZF2 2.1.3 app with Doctrine 2.
I installed using composer:
"zendframework/zendframework": "2.*"
,"doctrine/doctrine-orm-module": "dev-master"
A create a file config/autoload/database.local.php with the following:
return array(
'doctrine' => array(
'connection' => array(
// Default connection name
'orm_default' => array(
'driverClass' => 'Doctrine\DBAL\Driver\PDOMySql\Driver',
'params' => array(
'host' => 'localhost',
'port' => '3306',
'dbname' => 'zf2-experimental',
'user' => 'root',
'password' => '',
),
),
),
),
);
I create my entity Bar under Foo module (src/Business/Entity/Bar.php) and configure it on module.config.php like this:
'doctrine' => array(
'driver' => array(
__NAMESPACE__ . '_driver' => array(
'class' => 'Doctrine\ORM\Mapping\Driver\AnnotationDriver',
'cache' => 'array',
'paths' => array(__DIR__ . '/../src/' . __NAMESPACE__ . '/Business/Entity'),
),
'orm_default' => array(
'drivers' => array(
__NAMESPACE__ . '\Business\Entity' => __NAMESPACE__ . '_driver',
),
),
),
),
Ok! It's exactly at Sam says here!
Then I create a simple Foo entity and run the doctrine cli tool:
c:\wamp\www\zf2-Experimental>.\vendor\bin\doctrine-module.bat orm:validate-schema
[Mapping] OK - The mapping files are correct.
[PDOException]
SQLSTATE[28000] [1045] Access denied for user 'username'#'localhost' (using password: YES)
orm:validate-schema
c:\wamp\www\zf2-Experimental>
Looks like the cli tool can get my connection parameters in my config/autoload/database.local.php!
On Application index I tested my config:
$config = $this->getServiceLocator()->get('config');
\Zend\Debug\Debug::dump($config['doctrine']['connection']['orm_default']);
And this returned:
array (size=4)
'configuration' => string 'orm_default' (length=11)
'eventmanager' => string 'orm_default' (length=11)
'params' =>
array (size=5)
'host' => string 'localhost' (length=9)
'port' => string '3306' (length=4)
'user' => string 'root' (length=4)
'password' => string '' (length=0)
'dbname' => string 'zf2-experimental' (length=16)
'driverClass' => string 'Doctrine\DBAL\Driver\PDOMySql\Driver' (length=36)
Someone can, please, help me?! :)
Thanks you all!
Well, I waste a lot of time trying to solve this and finally did.
I forgot to mention that I using ZF1 environment-specific configurations style!
You can see here!
I create my database config file in the following structure (I didn't mention this before, because I thought It wouldn't interfere on the question):
'module_listener_options' => array(
'config_glob_paths' => array(
'config/autoload/{,*.}{global,local}.php',
// Here! My config path is config/autoload/app_env/development/
'config/autoload/app_env/' . (getenv('APPLICATION_ENV') ?: 'production') . '{,*.}.local.php',
),
So, my database configs actually are in config/autoload/app_env/development/database.local.php!
When I copy-paste the file to config/autoload/database.local.php my CLI Tool works!
But WHY? Why the Cli Tool can't look for the config file inside another directory?
There is a way to work with sub-folders?
Thanks for the help!
I'm looking for a tutorial on authentication with Zend 2 and Doctrine 2.
In particular the creation of the controller and adapter.
The official documentation is too global not help me enough.
thank you
EDIT:
i use "Doctrine Entity" (namespace User\Entity;)
The Entity is register in module.config.php file :
'doctrine' => array(
'driver' => array(
__NAMESPACE__ . '_driver' => array(
'class' => 'Doctrine\ORM\Mapping\Driver\AnnotationDriver',
'cache' => 'array',
'paths' => array(__DIR__ . '/../src/' . __NAMESPACE__ . '/Entity')
),
'orm_default' => array(
'drivers' => array(
__NAMESPACE__ . '\Entity' => __NAMESPACE__ . '_driver'
)
)
),
)
But now, how can i point my identityClass key to my adapter ?
Controller :
use Zend\Mvc\Controller\AbstractActionController,
Zend\View\Model\ViewModel,
Zend\Authentication\AuthenticationService,
Doctrine\ORM\EntityManager,
DoctrineModule\Authentication\Adapter\ObjectRepository as DoctrineAdapter,
User\Entity\User,
User\Form\UserForm;
class UserController extends AbstractActionController
{
protected $em;
public function setEntityManager(EntityManager $em)
{
$this->em = $em;
}
public function getEntityManager()
{
if (null === $this->em)
$this->em = $this->getServiceLocator()->get('Doctrine\ORM\EntityManager');
return $this->em;
}
public function getRepository()
{
if (null === $this->em)
$this->em = $this->getEntityManager()->getRepository('User\Entity\User');
return $this->em;
}
public function loginAction()
{
....
????????????
$adapter = new DoctrineAdapter();
$adapter->setIdentityValue($username);
$adapter->setCredentialValue($password);
$auth = new AuthenticationService();
$result=$auth->authenticate($adapter);
????????????
}
}
I've got this error : Call to a member function getRepository() on a non-object in ...doctrine\doctrine-module\src\DoctrineModule\Options\AuthenticationAdapter.php on line 132
line 123 : return $this->objectManager->getRepository($this->identityClass);
There are lots of ways to do it, but DoctrineModule for zf2 ships with a doctrine based authentication adapter (DoctrineModule\Authentication\Adapter\ObjectRepository). There is also a factory to create the adapter (DoctrineModule\Service\AuthenticationAdapterFactory). DoctrineMongoODMModule has it's module.config.php set up to use these services. (Note that the factory and adapter will work with ORM, but I'm not sure if the config keys have been added to DoctrineORMModule yet - perhaps someone who reads this would like create a PR for that?) These are the relevant config keys:
'authenticationadapter' => array(
'odm_default' => array(
'objectManager' => 'doctrine.documentmanager.odm_default',
'identityClass' => 'Application\Model\User',
'identityProperty' => 'username',
'credentialProperty' => 'password',
'credentialCallable' => 'Application\Model\User::hashPassword'
),
),
The identityClass is the doctrine document that represents your authenticated user. The identityProperty is the normally the username. getUsername will be called by the adapter to access this. credentialProperty is normally the password. getPassword will be called by the adapter to access this. credentialCallable is optional. It should be a callable (method, static method, closure) that will hash the credentialProperty - you don't need to do this, but it's normally a good idea. The adapter will expect the callable to have the following form: function hashPassword($identity, $plaintext).
To get the authentication adapter use:
$serviceLocator->get('doctrine.authenticationadapter.odm_default');
Note that all this only gives you an authetication adapter, it doesn't actually do the authentication. Authentication is done something like this:
$adapter = $serviceLocator->get('doctrine.authenticationadapter.odm_default');
$adapter->setIdentityValue($username);
$adapter->setCredentialValue($password);
$authService = new Zend\Authentication\AuthenticationService
$result = $authService->authenticate($adapter);
This will store the whole doctrine document of the authenticated user in the session object. If you want to store only the document ID in the session object, and retrieve the rest of the authetnicated user document form the DB each request, then take a look at DoctrineModule\Authentication\Storage\ObjectRepository. This provides a new StorageInterface for the Zend\Authentication\AuthenticationService.