Typically, codeigniter uses below structrue.
class AController extends CI_Controller
{
public function __construct()
{
parent::__construct();
$this->load->model('ModelA');
$this->load->model('ModelB');
$this->load->model('ModelC');
...
}
}
and I'm very new in codeigniter, I'm just wondering If I can make this more fast. Should I load these models whenever being made each request? It causes slow response.
In case of python tornado, they can store database model object so that all request share one model object. Is there any method like this in codeigniter?
You need to make sure your model is loaded before using it.
1.You can write it inside Controllers construct function so that you don't need to load the model inside other method.As example
class AController extends CI_Controller
{
public function __construct()
{
parent::__construct();
$this->load->model('ModelA');
$this->load->model('ModelB');
$this->load->model('ModelC');
}
public function index()
{
$this->ModelA->model_funtion();//now you can call model function for m any function of controller.
}
}
2.You can call it before using it.
class AController extends CI_Controller
{
public function __construct()
{
parent::__construct();
}
public function index()
{
$this->load->model('ModelA');
$this->ModelA->model_funtion();
}
}
3.You can load inside autoload.php.So that model can be used everywhere(inside any controller).
If you want it in most places, but not in all places, then as an alternative, you can create a Custom Controller and then Use it.
1. Code for /application/core/Custom_Controller.php :
<?php defined('BASEPATH') OR exit('No direct script access allowed');
class Custom_Controller extends CI_Controller
{
function __construct()
{
parent::__construct();
$this->load->model('ModelA');
$this->load->model('ModelB');
$this->load->model('ModelC');
}
}
2. Then Extend the Controller as :
include_once(APPPATH.'core/Custom_Controller.php');
class AController extends Custom_Controller
{
public function __construct()
{
parent::__construct();
}
public function index()
{
// Do something
}
}
Please try it..
class AController extends CI_Controller
{
function __construct(){
parent::__construct();
$this->load->model('ModelA');
$this->load->model('ModelB');
$this->load->model('ModelC');
}
public functionname()
{
$this->ModelA->modelfunctionname();
}
}
I realized the reusing is not possible, But I found better way.
something like this.
class AController extends CI_Controller
{
public function __construct()
{
parent::__construct();
$method = $this->router->fetch_method();
switch($method) {
case "method1":
$this->load->model('ModelA');
case "method2":
$this->load->model('ModelB');
break;
default:
$this->load->model('ModelA');
$this->load->model('ModelC');
...
}
}
Related
I am working on a blogging application in Laravel 8.
I have a settings table from which I pull the directory name of the current theme.
class ArticlesController extends Controller {
public $theme_directory;
public function index() {
// Theme _directory
$this->theme_directory = Settings::all()[0]->theme_directory;
// All articles
$articles = Article::all();
return view('themes/' . $this->theme_directory . '/templates/index', ['articles' => $articles]);
}
public function show($slug) {
// Theme _directory
$this->theme_directory = Settings::all()[0]->theme_directory;
// Single article
$article = Article::where('slug', $slug)->first();
return view('themes/' . $this->theme_directory . '/templates/single', ['article' => $article]);
}
}
The problem
A you can see, the line $this->theme_directory = Settings::all()[0]->theme_directory is repeted in both methods (and would be repeted in others in the same way).
Question
How can I avoid this repetition (and make my code DRY)?
Inheritance approach
Inheritance for a controller would avoid you from repeating it.
abstract class CmsController extends Controller{
protected $themeDirectory;
public function __construct()
{
$this->themeDirectory= Settings::first()->theme_directory ?? null;
}
}
Extend it and you can access it like you have always done.
class ArticlesController extends CmsController
{
public function index() {
dd($this->themeDirectory);
}
}
Trait
Use traits which is partial classes, done by just fetching it, as it is used in different controllers the performance is similar to saving it to an property as it is never reused.
trait Themeable
{
public function getThemeDirectory()
{
return Settings::first()->theme_directory ?? null;
}
}
class ArticlesController extends CmsController
{
use Themeable;
public function index() {
dd($this->getThemeDirectory());
}
}
Static function on model
If your models does not contain to much logic, a static function on models could also be a solution.
class Setting extends model
{
public static function themeDirectory()
{
return static::first()->theme_directory ?? null;
}
}
class ArticlesController extends CmsController
{
use Themeable;
public function index() {
dd(Setting::themeDirectory());
}
}
I am using core/MY_Controller.php and changed all my controllers to extend MY_Controller instead of CI_Controller. Now all the 'core' functions from CodeIgniter do not work on my regular controllers, for example: autoloaded models give an Undefined property error, and things like $this->load->... are not working aswell.
core/MY_Controller.php
<?php
defined('BASEPATH') OR exit('No direct script access allowed');
class MY_Controller extends CI_Controller {
public $test = false;
public function __construct()
{
$this->test = "test";
}
}
I initiate all my controllers with this:
<?php
defined('BASEPATH') OR exit('No direct script access allowed');
class Dashboard extends MY_Controller {
If you have a __construct() method in a class extending some other class, then you almost always need to call the parent constructor from the child.
Try this one simple addition to your constructor.
public function __construct()
{
parent::__construct();
$this->test = "test";
}
Try this first in the my controller
<?php
class MY_Controller extends CI_Controller {
public $data = array();
public function __construct()
{
parent::__construct();
$this->data['test'] = "test";
}
}
Then create a variable like public $data = array()
<?php
class Example extends MY_Controller
{
public $data = array();
public function index()
{
$this->load->view('example', $this->data);
}
}
View
<?php echo $hello;?>
I need help.
I'm trying to load a function from a model to a controller.
in my settings.php controller the function is this
<?php
defined('BASEPATH') OR exit('No direct script access allowed');
class Settings extends CI_Controller {
public function __construct()
{
parent::__construct ();
$this->load->model('update_model');
}
function test_result(){
$this->Update_model->test();
}
}
In my update_model
class Update_model extends CI_Model
{
public function test(){
return 'test1';
}
}
The error is this
A PHP Error was encountered
Severity: Notice
Message: Undefined property: Settings::$update_model
Filename: controllers/settings.php
Line Number: 14
Fatal error: Call to a member function test() on null in C:\xampp\htdocs\activations\application\controllers\settings.php on line 14
Please help.
Thanks
update controller
<?php
defined('BASEPATH') OR exit('No direct script access allowed');
class Settings extends CI_Controller {
public function __construct()
{
parent::__construct ();
$this->load->model('update_model');
}
function test_result(){
$this->update_model->test();
}
}
update in Update_model
<?php
class Update_model extends CI_Model
{
function __construct() {
parent::__construct();
}
public function test(){
return 'test1';
}
}
write small first letter when call method of model in controller.$this->update_model->test();
I've got a BaseController in a Laravel Framework based App with the following code:
class BaseController extends Controller {
public function __construct(Credentials $credentials) {
$this->credentials = $credentials;
}
Then, all my other controllers will Extend the BaseController:
class PostController extends BaseController {
public function __construct(PostRepository $post)
{
$this->post = $post;
parent::__construct();
}
However, I'd need to type hint the Credentials Class in the parent::__construct(); of all my controllers. Is there any way to avoid that?
Thanks in advance
I can solve it using the following code:
class BaseController extends Controller {
public function __construct()
{
$this->credentials = App::make('Credentials'); // make sure to use the fully qualified namespace of Credentials if need be
}
}
class model_demo extends CI_Model{
function model_demo()
{
parent::Model();
}
}
I'm working with CodeIgniter with a constructor, and it's producing a fatal error.
class model_demo extends CI_Model{
function model_demo()
{
parent::__construct();
}
If you are using Codeigniter 2 or abore, try:
class model_demo extends CI_Model
{
function __construct()
{
parent::__construct();
}
}
You can see the syntax here:
Models: Codeigniter User guide