I use Module Autoloader to autoload resources (forms, Doctrine models etc.).
I do not use Zend_Db_Table at all.
When I load any Doctrine model,
e.g. MyModule_Model_Test,
it tries to load MyModule_Model_TestTable too, so I get errors that the MyModule_Model_TestTable.php is missing.
To fix this, I may create empty class MyModule_Model_TestTable class and
everything works as expected.
But I don't need this file.
Strange that, when I move MyModule_Model_TestTable to /anyDirDeeper/MyModule_Model_TestTable without changing its name or content, the class is correctly loaded too…
How to configure Module Autoloader so it would not require this …Table classes?
I have in my application.ini:
resources.frontController.moduleDirectory = APPLICATION_PATH "/modules"
resources.modules[] =
And Module Bootstrap:
class MyModule_Bootstrap extends Zend_Application_Module_Bootstrap {}
My app structure is similar to this:
/application/
/modules/
/mymodule/
/models/
/Db/
*Mymodule_Model_Db_Test*
*Mymodule_Model_Test*
I think this issue was produced because I used the same module name and resource type name (registered by default).
Models were named: Acl_Model_Modelname and Acl_ namespace was registered with autoloader. Changed model namespace to something else and it works.
Related
Like in Codeigniter we do have 'core' folder where we can define our own controller like 'MY_Controller' and can be used to extend all the class to extend from this controller is there any possibility to do so in Symfony2.
In symfony I want to create class 'MY_Controller' which extends from the base class 'Controller', and I want all the classes in the controllers to extend from MY_Controller' class.
Thanks in Advance...
Note:
When working with Symfony2 it is strongly recommended you follow the Symfony2 coding style. It's basically the same as PHP-FIG, with one or two deviations. So underscores are a no-no in class names. Other than that: Symfony is pretty easy to work with, and fully OO, so changing the class a controller extends from is as simple as replacing extends Controller with extends AnotherClass.
But now, the symfony2-way of using a custom controller:
What you could do, is create a Core bundle (CoreBundle henceforth). Then, in this CoreBundle, define a controller, that extends from the Symfony Controller component. From the command line, in your project root, use this command:
php app/console generate:bundle --namespace=YourNameSpace/CoreBundle --bundle-name=YourNameSpaceCoreBundle
More options can be found here
After that, you'll find a DefaultController class in the bundle directories. (probably in the folder src/YourNamespace/CoreBundle/Controller). Then, set about generating your Core controller:
php app/console generate:controller --controller=YourNameSpaceCoreBundle:Core
See the documentation for more options on how to generate your core controller.
After you've finished setting up your custom controller, you can use it in any of the other bundles at will:
namespace YourNameSpace\AnotherBundle\Controller;
use YourNameSpace\CoreBundle\Controller\CoreController;
class DefaultController extends CoreController
{//extends from your custom controller
}
And that's it: you're done.
First, don't name the class using underscores as in PSR-0 each underscore char is converted to a directory separator, when used in class name.
Second, put your controllers to <bundledir>/Controller/
Third, name your controller something like BaseController and extend all other controllers from it.
Fourth, think of using dependency injection rather than coupling functionality in a base controller.
I'm trying to integrate PHP namespaces into an existing Zend Framework project (v1.12). When I add namespacing at the top of a working controller, it doesn't work anymore and the application throws an Invalid controller class error. Here's my controller definition :
namespace MyProject\Controller;
use MyProject\Controller\MyRestController;
class MyFooController extends MyRestController
{
}
and the init method within the Bootstrap.php:
protected function _initAutoload()
{
$autoloader = Zend_Loader_Autoloader::getInstance();
$autoloader->registerNamespace('MyProject');
return $autoloader;
}
Just a guess (have not used ZF for quite some time): Zend will not accept any class as a controller, just those extended from the framework's base controller class. As you don't extend from the frameworks base controller class you see the error.
If that is the reason, take care you initially extended from the base framework controller class or you implemented the needed interface.
namespace MyProject\Controller;
class MyRestController extendes Zend_Framework_Base_Controller_Class_Name_Here
{
...
p.s. the use MyProject\Controller\MyRestController; looks superfluous as that class is in that namespace already. Let's review your code:
namespace MyProject\Controller;
This sets the namespace of the file. That means, non-FQCN will resolve into it. For example:
new MyRestController();
Resolves to the following FQCN:
new MyProject\Controller\MyRestController
Which - oha! - is exactly what you wrote in use:
use MyProject\Controller\MyRestController;
Which means, that this use clause is superfluous, the extend in:
class MyFooController extends MyRestController
Would go to it anyway at first. Because it's the same namespace.
I am facing similar problem now. For me this looks like that Zend cannot properly resolve namespaced controller name. So when I put for example IndexController into namespace \Basic\Controller, it will be not loaded because Zend want to load \IndexController class, which does not exist.
I am thinking about extending standard zend router class, which has method getControllerName.
Then I can set this in bootstrap by:
$router = new \My\Namespaced\Router();
$front = Zend_Controller_Front::getInstance();
$front->setRouter($router);
I didn't tried that code yet but this should work.
How can someone autoload every form and model for each module? Consider the following file structure:
application/
modules/
foo/
forms/
Register.php
models/
Account.php
Bootstrap.php
bar/
forms/
Publish.php
models/
Article.php
Bootstrap.php
Bootstrap.php
And for example, in foo/Bootstrap.php you have the following (non-functional) code:
class Foo_Bootstrap extends Zend_Application_Module_Bootstrap
{
protected function _initAutoLoad()
{
$loader = new Zend_Loader_Autoloader_Resource(array(
'basePath' => APPLICATION_PATH . '/modules/foo',
'namespace' => 'Foo',
));
$loader->addResourceType('form', 'forms', 'Form')
->addResourceType('model', 'models', 'Model');
return $loader;
}
}
Basic question: How can the bootstrap be modified so that it does load every form and model from the Foo module?
Extra question: Is it possible to have a global autoloader that loads in forms and models from every module? If so, how?
Edit (most common questions about the issue):
The default Zend naming conventions are being used for classes. Such as Bar_Model_Article, Bar_Model_Mapper_Article, Bar_Model_DbTable_Article, Bar_Form_Publish, ... (And are being placed in their respective folder.)
It isn't just one module that doesn't get its classes loaded, it's all of them.
There is no problem autoloading classes using the Zend autoloader when using a plain no-module application with multiple models, mappers, dbtables and forms.
Fix
As #Tim Fountain mentioned the module bootstraps weren't being run, meaning none of the automatic loading occurred that's baked into Zend. Eventually, I found where the problem was in my case. I had to remove the following lines from my configuration:
bootstrap.path = APPLICATION_PATH "/Bootstrap.php"
bootstrap.class = "Bootstrap"
Agreed, the global bootstrap won't work anymore; but it's a lot better than having module bootstraps not functioning. If anyone knows how to still have the global bootstrap, feel free to leave a comment. Hope this can be of help to others with a similar problem.
The module bootstrap class sets up the module autoloader automatically, so you can remove your example _initAutoload() function leaving just an empty class and it should all just work. See: http://framework.zend.com/manual/en/zend.loader.autoloader-resource.html#zend.loader.autoloader-resource.module
Edit: It sounds like your module bootstraps aren't being run. This is not an uncommon problem as the way it all fits together can be a bit confusing. The quickest way to verify this would be to just add an init method to one of them with an echo and an exit and see if it ever gets output.
Module bootstraps are pulled in and run by the 'modules' resource within Zend Application. You need to trigger this resource in some way because ZF won't go hunting around for module bootstraps just in case they are there. The most common way to do this is to include this line in your application.ini:
resources.modules[] = ""
alternatively you can manually setup the resource from your main Bootstrap file.
I also had it always like that. But since the release of 1.10 (wild guess), you can remove that bootstrap code and just put the following line in your application.ini:
appnamespace = "Foo"
I personally leave mine empty.
I tried to search here before creating this, but I couldn't find anything.
I have a simple project without modules and I'd like to load my models (which are inside application/models) without using any namespace and without usign any extra loading lines.
Basically what I want to do is to have my class Projects extends Zend_Db_Table_Abstract inside my models folder and to load it in my controller using $db = new Projects();
Is there anyway to do this? Is it recommended to use Model_Projects instead?
What If I had modules?
Edit:
I tried to use this without any other implementation and I got Class 'Projects' not found
It is because the Projects class is not autoloaded. Depending on your application namespace, (for example the default namespace 'Default') you have to name your class into something like: Default_Model_Projects
The ZF Docs reference 'Subclassing the Action Controller' (bottom of the page), but don't reference a standard place to put the new Action_Controller class.
Application_Module_Autoloader sets up pats for a bunch of things, but never controllers. I guess putting it on library/APPNAMESAPCE/Action/Contoller would work. But that seems a bit odd since every other application specific file is stored under application/.
The class gets autoloaded like any other class, there isn't a 'standard' place for it as such. So the question becomes, where do you want it to live?
The convention I usually follow in modular applications is to have most stuff in the modules, but register an app namespace and use application/models for 'core' type classes. So in your case, say your app namespace was Wordpress, you'd have:
class Wordpress_Controller_Action extends Zend_Controller_Action
{
}
and the file would live in application/models/Wordpress/Controller/Action.php.
To make this work you'll need application/models on your include path, and you'll want to init the standard autoloader with something like this (in your bootstrap class):
protected function _initAutoloader()
{
$autoloader = Zend_Loader_Autoloader::getInstance();
$autoloader->registerNamespace('Wordpress_');
return $autoloader;
}
alternatively you could setup the above in application.ini.