Cakephp using model wtihout defining model file - php

I am new to cakephp and trying to customise a cake application.
I have seen they are using models without having model class files in app/models folder
I think there is an automatic mapping from table to model
I am sharing some usefull lines of codes
public $uses = array('LinkEmperorCampaignDetail','Configuration','Article');
$this->paginate = array(
'conditions' => $condition,
'limit' => 10
);
$this->set('articles', $this->paginate('Article'));
As you have seen its importing Article model using $uses variable, there is a table "articles" in database, But there is no file Article.php in app/models. I have deleted cache folder and disabled caching.
I have checked if it is automatic, by creating a table "test" and used this code
$test=$this->test->find('all');;
var_dump($test);exit();
but getting this error Error: Call to a member function find() on a non-object
Please let me know how this is happening
Thanks,
Lajeesh

Change it to:
$test = $this->Test->find('all');
Also, please, check cakephp model and database conventions

Model files are optional
Cake will user an AppModel instance if there is no model file found:
CakePHP will dynamically create a model object for you if it cannot find a corresponding file in /app/Model.
As such a reference tothis->Article will be an instance of AppModel as the model is declared in the $uses variable but a model file doesn't exist.
That doesn't mean $this->RandomModel works
Referencing a random model, as seen in the question, will simply produce the following error:
Call to a member function find() on a non-object
That's to be expected because the controller knows nothing about the Test model from the code in the question.
The optional model file handling does not mean that you can reference any model by expecting it to exist as a Controller class property. $uses exists for the purpose of telling the controller which models it needs to know about. If a model is only needed in specific circumstances, loadModel exists for this purpose:
$this->loadModel('Test');
$stuff = $this->Test->find('all');

Related

Accessing other model file within another model file

I am trying to create an class inside the model directory. This class(eg:- Admin) exposes only the methods which makes sense to the controller.
The Admin class will do all the joins and stuffs internally on tables(using ORM) and prepares data which can be readily consumed by the controller.
I have created 15 files in the model directory each of them representing a table in my database using the ORM method.
Now I want to create to create an instance of table within the Admin classes' get_All() method. I have tried to use Kohana::factory() which was unavailable in my Admin class. I tried to create the instance using the 'new', but it ended in an error which says that the specified class is not found.
My class definition for Admin is as follows
<?php defined('SYSPATH') or die('No direct script access.');
class Model_Admin {
public function get_All()
{
$PD = new Model_PayPalData;
echo 'Success';
}
}
The error is:
ErrorException [ Fatal Error ]: Class 'Model_PayPalData' not found
APPPATH/classes/Model/admin.php
Please advice on how to deal with this situation.
Thanks for your attention
Seem like your class is not loaded. You can check this by viewing the declared classes
get_declared_classes();
If it is't there, make sure to include it, or add it to the Models directory, if needed without extending the ORM class.

CakePHP: Call to a member function set() on a non-object error

My controller seems to be buggy here:
public function addAdmin($id) {
$this->User->id = $id;
$this->User->set('role','admin');
$this->User->save();
}
So it throws me the error Call to a member function set() on a non-object.
Actually, I want to update the field 'role' in a table column called 'role' and set it to 'admin'.
Can you imagine what's wrong? I've seen many tutorials using this with success but here apparently i'm missing something.
PS: I'm a cakephp newbie :D
Thank you in advance!
The User model isn't loaded.
Try loading it:
public function addAdmin($id) {
$this->loadModel('User'); // here
$this->User->id = $id;
$this->User->set('role','admin');
$this->User->save();
}
You don't have to load a model if you're in the Controller of that Model - but in this case, you're in a different Controller, so you either need to load the model (like above), or access it via an already-loaded associated model.
So, as an example, if you're in the RolesController, you could access the associated 'User' model without having to specifically load it:
$this->Role->User->set('role', 'admin');
Seen your code, your calling User from AdminsController.
Unless you do a
var $uses = array('Admin', 'User');
on the beggining of the controller (don't do it though, it affects performance), it won't recognize your User model. By default AdminsController only has direct access (that is, using $this->Admin) to Admin model, FoosController to Foo model (with $this->Foo), etc.
You can do as #Dave indicates in his answer, but do have in mind, if Admin is related (with hasMany, belongsTo, or any other association) with the User model, then you can access the User model from the AdminsController like this
$this->Admin->User->set(1,2);
And if you have a Foo model associated with User, for example, the same concatenation rule applies, and in your AdminsController you can do
$this->Admin->User->Foo('find')
(A lot of concatenation like this affects performance).
loadModel works for me! I initially tried using a model function that called two different models but instead I created a a model function for each model and then called functions in a single controller.
if ($this->Transaction->saveTrans(PARAMETERS)){
$this->Session->setFlash(__('Transaction Success!'));
$this->loadModel('Creditcard');
if ($this->Creditcard->saveCC(PARAMETERS)){
$this->Session->setFlash(__('Credit Card Success!'));
} else {
$this->Session->setFlash(__('Unsuccessful: The Credit Card was approved but could not be saved. Please try again.'));
}

Call to a member function find() on a non-object with extended model

I have an "Admin" model which extends another model "User" which extends the "AppModel".
I have a controller "ApisController" in which I am trying to query the data from the admins table.
So I'm doing something like this:
$admins = $this->Admin->find('all');
But when I do that, I get the following error message:
Error: Call to a member function find() on a non-object
File: /home/farhan/www/core/app/Controller/ApisController.php
Line: 9
If I try to do the same thing in a controller "AdminsController", everything works fine. So I'm not sure what I'm doing wrong. I'm new to cake, so I understand if this is a simple error.
If you have ApisController and want to use an "Admin" model (which clearly is not the singular form from "Apis" - it would probably be Api), you need to manually declare your used model:
public $uses = array('Admin');
Then the controller has the "Admin" model available as primary one.
Book
Default is that cake tries to find the right one based on inflection:
PostsController => Post model
(plural => singular)

Using CakePHP model class

I'm just studying CakePHP so sorry for any obvious mistakes.
I have created model class and changed default table name.
class Weathers extends AppModel {
public $tablePrefix = 'weather_';
public $useTable = 'forecasts';
function saveCountries($countries){
...
}
}
And my controller function
if (!$this->loadModel('Weather'))
exit;
$Weather = $this->Weather;
$Weather->saveCountries($countries);
I'm getting error on $Weather->saveCountries($countries);
Error: Table weathers for model Weather was not found in datasource
default.
Please help find out what I do wrong.
The Model class you defined is Weathers not Weather. So just change the class name Weather instead of Weathers and this is done.
Note the declaration of your Model class.
You've called it Weathers.
There is no problem with this. However, as you are trying to then load the model Weather (not the lack of plural in this case) CakePHP is constructing a model dynamically for you, instead of using your Weathers (plural) class.
The CakePHP standard is to use a singular name for models. I suggest that you rename your model class to Weather to avoid this issue. Once you make this change, the code that you have for loading the model will work as intended.

Which models can I access from a controller in CakePHP?

Suppose I have the classic Post model and I've created an Author model too.
I have some basic questions:
The Post object is automatically created whithin the PostsController?
In order to create an instance of Post whithin AuthorsController, is the only way with
$this->Post = ClassRegistry::init('Post');
Please notice that by doing " $this->Post " I assume the Post variable will be created in this line. Am I right ?
Thank you in advance!
Look into model associations. If your associations are set up properly, you will be able to do
$this->Author->Post
to access the Post model from the Authorscontroller. If the model was not related but you still needed to access it, you could do so using the $uses array.
In terms of your first question, you are correct. All of your controllers extend Appcontroller which imports the default cake Controller class found in /lib/. You can see on line 376 in the cakePHP controller file here that the model whose name is equal to the class name is loaded, after all of the models given in the $uses array are loaded.
All models in your uses array
You can access $this->MmodelName for all models declared in the uses property - If this property is not declared it defaults to the model corresponding to the controller - i.e. PostsContorller -> Post model.
Models declared in $uses as created/instanciated on first reference - i.e. they are lazily created.

Categories