CodeIgniter Base Classes: Keeping it DRY

Posted: 2010-02-08
Category: CodeIgniter

Most applications in CodeIgniter will have various types of pages. The public frontend, a backend admin panel, perhaps some sort of moderator or staff panel, etc. Logic for these types of pages is normally copied between all of their different Controllers which means, for example,  if the way the admin area protection is handled is changed there will be lots of Controllers to change and test. This logic can instead be shared by some creative extending of the Controller class to create custom Base Controllers like Public_Controller, Admin_Controller, etc.

WTF are you talking about?

The idea is that most of your controllers share something in common with each other. For example: All admin controllers need to make sure a logged in user is present and that they are an administrator. A public controller may want to load a theme for your application and load default user data, navigation links or anything else frontend related.

Wicked! How?

The first step is to create these Base Controllers.

application/core/MY_Controller.php

MY_Controller is a basic core library extension. Whenever you create a class with the MY_ prefix the CodeIgniter Loader class will load this after loading the core library, allowing your code to replace/extend the core library. We won't be replacing anything, but we will be adding to it.

class MY_Controller extends CI_Controller
{
 function __construct()
 {
  parent::__construct();

  $user_id = $this->session->userdata('user_id');
         $this->data['user'] = $this->user_lib->get($user_id);
        }
}

All we have done here is create a base class that all of our Controllers and "controller types" will inherit. Anything we put in here and assign to $this will be available to anything that extends this class.

application/core/Public_Controller.php
class Public_Controller extends MY_Controller
{
    function __construct()
    {
        parent::__construct();
        
        if($this->config->item('site_open') === FALSE)
        {
            show_error('Sorry the site is shut for now.');
        }

        // If the user is using a mobile, use a mobile theme
        $this->load->library('user_agent');
        if( $this->agent->is_mobile() )
        {
            /*
             * Use my template library to set a theme for your staff
             *     http://philsturgeon.co.uk/code/codeigniter-template
             */
            $this->template->set_theme('mobile');
        }
    }
}

Public_Controller is pretty much the same, but you can see we have some frontend-only related code here. The first statement will check to see if the site is currently open using a theoretical settings library that your application might habe and shows an error if the site is closed. The next statement uses the user agent library to offer a mobile version of the site to anyone on a mobile device.

application/core/Admin_Controller.php
class Admin_Controller extends MY_Controller
{
    function __construct()
    {
        parent::__construct();
        
        if($this->data['user']['group'] !== 'admin')
        {
            show_error('Shove off, this is for admins.');
        }
    }
}

Admin_Controller is again fairly similar. It uses a generic sort of user level checking to see if the user is an admin and shows an error if not.

Connecting Base Controllers to Controllers

While there are a few ways to do this, the easiest is to use PHP 5's wonderful __autoload() magic function. By placing this at the bottom of your config.php you can make it load early enough to run before the Controller and it will be somewhere that wont get overridden on upgrade.

/*
| -------------------------------------------------------------------
|  Native Auto-load
| -------------------------------------------------------------------
| 
| Nothing to do with cnfig/autoload.php, this allows PHP autoload to work
| for base controllers and some third-party libraries.
|
*/
function __autoload($class)
{
 if(strpos($class, 'CI_') !== 0)
 {
  @include_once( APPPATH . 'core/'. $class . EXT );
 }
}

Now the Base Controllers are being made and loaded, you need to inheriting them in your Controllers. So instead of the usual...

class Blog extends CI_Controller
{
    function __construct()
    {
        parent::__construct();
        // Whatever
        $data['stuff'] = $whatever;
    }
}

use...

class Blog extends Public_Controller
{
    function __construct()
    {
        parent::__construct();
        // Whatever
        $this->data['stuff'] = $whatever;
    }
}

And there you have it! In your Controller you'll have all your data set in MY_Controller or other Base Controllers available in $this->data, so pass that to your views and it will be available. You can also use $this->load->vars('foo', $bar) in your Base Controllers to set values that are only available in your views.

Summary

Base Controllers are a nice simple way to give you global data, logic and shared code which can be specific to a certain part of your site. They can do all sorts of crazy stuff which I will leave for you to think about.

Please post your most inventive uses in the comments section.

Comments

Gravatar
Dave Bowman

2010-02-09

Simple, but effective technique, Thanks, Phil. There's this one thing though, I'm not sure about: it is supposed to be an ill practice - suppressing possible errors with @. Wouldn't it be more "righteous" to check if file_exists and if it does, then include it in normal way, thus presenting the possibility for it to eloquently fail?

Gravatar

2010-02-09

@Dave Bowman: I considered doing it this way, but it's an extra check we don't need. If a file does not exist then it will throw a "Class does not exist" fatal error anyway, so by just trying to include then saying "meh" it doesn't make any real difference.

I don't like to make a habit of using @ but I don't think it should be considered bad practice. The error will still show in the error logs and if you truly don't care about whether something works or fails it is perfect.

Gravatar
Bradfields

2010-02-11

I like it. I've definitely gone about this kind of thing the long-winded way in the past and included things like permission checks in the top of every controller.

I'll be testing out this method in my next CI project so props from me.

Gravatar
Sam Bruner

2010-02-12

Great article,
few weeks ago I read the posts of this guy: http://blog.umnet.co.il/ about developing cms with codeigniter, and He also talked about that.
So for newbies all this info is very useful.

Gravatar
Zoran

2010-02-15

This is good idea which i am using also, in your __autoload method, you can check for Controller's children classes( Admin_Controller and Public_Controller) and load only them, cause it won't be good idea to load other classes that you only need in only few application controllers.
This is the best way, cause you are extending the system the way it is built.
Really good post. Thank you

Gravatar
Codemagician

2010-02-19

May this code live for ever. Please keep it on the most secure server on the planet, clone to keep alive! :D

Thanks heaps. I wonder why this is so hard to find at CI head quaters. Don't people build reusable code in PHP land? ;)

Cheers :)

Gravatar
Nguy?n ?ình Trung

2010-03-04

I'm just getting used to those OOP approach. Although it can help me reduce the number of line to write, it just keep bloating up by the time. Keeping dynamic super variables for the child Controller to override is such a complex task.
I found it very difficult to maintain the code this way, because I have to keep eyes on parent classes as well as child class. Or maybe my classes just too poor designed.

Gravatar
Ionut Marinescu

2010-03-09

i tried to use your method but i get a error in the function __autoload it tries to load application/libraries/Model.php
i have some autoloaded models in autoload.php not sure if that is the problem

Gravatar
Dimas

2010-03-10

Is there any benefit of doing one or the other?

1) having MY_controller.php and putting it in the libraries folder or ...
2) just creating a Base_controller.php in your controllers folder and then having any new controller extend it?

Or is it just a matter of preference? It seems that you do both above ...

Gravatar
David

2010-03-17

Hi,

when loading a model, i had the same error as Ionut Marinescu :

Message: include(~/application/libraries/Model.php) [function.include]: failed to open stream: No such file or directory

and

Message: include() [function.include]: Failed opening 'C:\wamp\www\outils/Yhoi8_yt%kjZd23/application/libraries/Model.php' for inclusion (include_path='.;C:\\php5\\pear')

Gravatar
Obolus

2010-03-17

This is swell until you need to load libraries or models. Thanks for the write-up in any case.

If an project requires separation like this, it would be better to go with Kohana. Until the next CI release anyway.

Gravatar
Jim Wardlaw

2010-03-17

Great work Phil.
Solved my issue with distributing a shared admin system across multiple sites like a dream!

Gravatar
Carlos

2010-03-18

I would like share this MY_Model class with you
http://csotelo.blogspot.com/2009/10/model-library-for-codeigniter-php-if.html

Gravatar

2010-03-18

@Dimas: Neither method is better or worse, they are two different things. For any code that you want in EVERY controller, use MY_Controller. For code you want in SOME controllers, use the named method.

Gravatar

2010-03-18

@Obolus: What do you mean? you can load models and libraries just as you do now. The autoload obviously will allow you to load libraries directly if they support it, but that really is not the point of the article.

CodeIgniter does not require this functionality to run, it is a Don't Repeat Yourself step that can be translated to almost any framework. Kohana does not support this out of the box, but you could implement it very similarly.

@Carlos: Jamie Rumbelow has created a MY_Model which I have been contributing too which I use in all my projects.

http://github.com/jamierumbelow/codeigniter-base-model

Gravatar
Twisted1919

2010-03-24

What if you do something like :
libraries/MY_Controller.php

class MY_Controller extends Controller{

protected $data ;

public function __construct(){
parent::Controller();
$this->data['blah'] = 'Something available on Front and Backend'
}

}
//Same file
class Frontend extends MY_Controller{

public function __construct(){
parent::__construct();
//load here something needed only on frontend etc .
}

}
//Same file
class Backend extends MY_Controller{

public function __construct(){
parent::__construct();
//do something here for backend only.
}

}


What's wrong if you do like this ?

Gravatar
Buso

2010-03-27

Thanks for the tips phil.

Im gonna have to agree with Zoram though:

Isn't it better to change the if condition to something like..

$class=='Public_Controller' || $class=='Admin_Controller'

?

Gravatar
Cahva

2010-03-29

Just had to drop in and thank you for a very good post! I've changed using this new autoload from now on. I dont even use MY_Controller anymore. Instead I do a Base_Controller which describes the base controller better than MY_Controller :)

Gravatar

2010-03-29

@Buso: I did not see what Zoran was getting at. There is no issue with allowing an autoloader to potentially load any library as it gives you flexibility to use static classes if you like.

There would be no point in restricting it to ONLY load controller base classes, as that is two conditions that don't need to be run. In trying to make it more efficient you are actually slowing things down and restricting your possibilities.

Gravatar
Kyle

2010-04-06

So, I'm using a MY_Controller like you did above, and I'm trying to redirect('signin'); if no one is signed in, but it won't work. Does a MY_Controller constructor not allow redirect(), because they work in normal controller constructors?

Gravatar
Mike

2010-05-27

It's a good idea to restrict the loading like Buso explained. If you don't restrict it and watch your log files you see that it tries to load MY_ functions that can not be found. This is because they don't exist, are placed within other files (bundle all ..._Controller classes within MY_Controller.php for ex.) or are not at the right place (there is a lybraries and core folder). At the same time if you look at the benchmarks, not restricting it will slow down the application al lot. 0.6 or with restrictions 0.03.

Gravatar
Mike

2010-05-27

If you don't want the error messages within the log files (and want to keep the static flexibility), use:

function __autoload($class)
{
if (strpos($class, 'CI_') !== 0)
{
if (is_file($location = APPPATH.'libraries/'.$class.EXT))
{
include_once $location;
}
// core folder is used by CodeIgniter 2
else if (is_file($location = APPPATH.'core/'.$class.EXT))
{
include_once $location;
}
}
}

If you want to restrict to specific classes, use:

function __autoload($class)
{
if (strpos($class, 'CI_') !== 0)
{
if (in_array($class, array('MY_Controller', 'MY_Lang'))) // etc.
{
if (is_file($location = APPPATH.'libraries/'.$class.EXT))
{
include_once $location;
}
else if (is_file($location = APPPATH.'core/'.$class.EXT))
{
include_once $location;
}
}
}
}

Gravatar
Simon Carr

2010-08-16

Hi Phil,

Great tutorial. I have have an application where controllers need to share information between each other and have been trying to find a way for controller B to share data with the view after being loaded by controller A. If I put a var $view_data = array() in my sub class, then any controller that extends that sub class can add whatever data it wants to the shared properties. $this->view_data['site_name'=>'My site']

Seems simple but will make a hughe difference.

By the way i love the new pod cast, that is where I got wind of sub classing.

Simon

Gravatar
Ross

2010-08-23

does this still apply with CI2.0?

Am having some difficulties implementing it. But then this could just be me being useless at CI in general and not a 2.0 issue.

I have the MY_Controller in application/core, and the Admin_Controller also in application/core

getting ~
Fatal error: Class 'Admin_Controller' not found in

thanks.

Gravatar

2010-08-25

@Ross: Two possibilities, you have either forgotten to add __autoload() to your config.php or you are using an old version of Modular Separation (which overrides __autoload()) that does not check in /application/core. If you use MS, try upgrading the 2.3.

Gravatar
Ross

2010-08-26

@http://philsturgeon.co.uk/
upgrading MS appears to have done the trick, thanks !

Gravatar
Brian

2010-09-13

Nice! This will help me overcome an obstacle in my current project. Thanks for the DRY tutorial.

Gravatar
Harman

2010-10-08

@ is good or bad it's just depend on your coding style or on your mind. for me normally it's bad practice. i am avoid using Error suppression because i believe if error exist try to resolve it not suppress it.

//sorry for my poor English

Gravatar
Jordan Arsenault

2010-10-12

Hey all,

Followed the instructions above - great post.
Phil, (or anyone)...One quick question regarding the last couple sentences of your post:

You wrote: "You can also use $this->load->vars('foo', $bar) in your Base Controllers to set values that are only available in your views."

I'm looking to make some global variables available in my views - how do I go about accessing them from a view? I put the following into MY_Controller:

8< --- 8< --- 8< --- 8< --- 8< --- 8 '123',
'test2' => 'abc'
);

$this->load->vars($config);

8< --- 8< --- 8< --- 8< --- 8< --- 8

Gravatar
Brian Dichiara

2010-10-15

I have followed these steps and everything seems to be working fine, however when I try to enable the profiler ($this->output->enable_profiler(TRUE);) I get the following error:
Fatal error: Call to undefined method stdClass::_assign_libraries() in C:\htdocs\ci-1.7.2\libraries\Loader.php on line 1035
Using CI 1.7.2, Any suggestions?

Gravatar
Randy Cram

2010-11-18

Hey there,

Just wanted to share something I posted on the CI forums about using Phil's guide here with CodeIgniter 2.0:

http://codeigniter.com/forums/viewthread/173797/

Gravatar
Jason

2010-12-15

Hey Phil.... Followed your steps and everything works as it should until I try extending a controller that I have within a sub folder.

IE:

/controllers/admin/welcome.php

class Welcome extends Admin_Controller {

Admin_Controller.php being in:

/libraries/

If I take the controller out of the sub folder and back into the root controller folder it works just fine.

Any thoughts?

Thx!

Jason

Gravatar
Johnny

2010-12-22

@Jason - Make sure you've got that bit of code at the bottom of your config file and that you're running CodeIgniter 2. I'm running a similar setup and it works for me. I have controllers like: /controllers/backend/overview.php that are successfully extending my Global_Controller in /libraries/.

@phil - quick question. I love the global controller idea. I wonder is their and way to do something on every page load AFTER the controllers are loaded. For example, I want to implement and "Maintenance Mode" where you could set $maintenance_mode = TRUE; in the Global_Controller (for site wide maintenance) or in the Backend_Controller (for backend maintenance only) or in a normal controller (in the __contruct or any other method). So, I need to know if there's any single place where I can put the code to check if $maintence_mode has been set to TRUE. I know this is not specifically related to your post but I thought with your knowledge of CI you'd know before anyone else. Thanks.

Gravatar
Johnny

2010-12-23

@Jason - I misspoke. You do not need CI 2 for this to work. I just happen to be using version 2. Sorry.

Gravatar
Gene Ronquillo

2010-12-28

Hi Phil, I have a similar approach - MY_Controller extends CI_Controller in core and Admin_Controller extends MY_Controller in libraries.

Without the native autoload code, Class Admin_Controller cannot be found. Why?

Doesn't CI natively allow extending extended classes?

Gravatar

2010-12-31

@Gene: Nope! CodeIgniter would have no way to know where this file is. CodeIgniter.php will look for a MY_Controller manually, but it cannot know what Admin_Controller is unless you tell it somehow, either with a manual include in the controller or __autoload().

Gravatar
Rob Allport

2010-12-31

Wow, great stuff and great article. I seriously love how everything can be so organised in CI!

Gravatar
Ami Creative

2011-01-04

Stuff like this should be in the official codeigniter user guide (along with organising nested views!) :)

Gravatar
Karl Ballard

2011-01-19

I was dong this last night and I did it perfectly, however.. I then moved the new controllers into a separate folder within libraries. But then I loaded a custom library and it was trying to autoload that within the 'core_controller' folder with a prefix of 'MY_'.

What would be the best workaround in your opinion, would it to restrict the classes the auto loader loads?

Gravatar
Rj

2011-02-03

do we need to change "libraries" to "core" for 2.0?

Gravatar
Joseph Taylor

2011-02-03

Phil, thanks for updating this. I've implemented it immediately! I noticed you still show the path for MY_Controller to be "libraries/MY_Controller" but it didn't work until I moved it to the "core" folder along with Public and Admin...

Does this mean all "MY_" classes should go in "core" from now on?

Gravatar
Calvin Froedge

2011-02-04

Right on Phil! Thanks fore sharing the knowledge - I was trying to do this the 1.7 way. This is much more elegant = ) +1 for better abstraction!

Gravatar
John

2011-02-24

Ok, I get Fatal error: Class 'MY_Controller' not found in ....../application/controllers/welcome.php on line 3

I did

MY_Controller.php located in application/core
class MY_Controller extends CI_Controller
{
function __construct()
{
parent::__construct();
}
}

welcome.php
class Welcome extends MY_Controller {

function __construct()
{
parent::__construct();
}


and at the end of the config.php file
function __autoload($class)
{
if(strpos($class, 'CI_') !== 0)
{
@include_once( APPPATH . 'core/'. $class . EXT );
}
}


ANY ideas why its giving me this error?

Gravatar
John

2011-02-24

Nevermind, misspelling in file name will do it. DOOHH

Gravatar
A.

2011-03-14

Im getting blank page? Is all code correct?

Gravatar
Rafael

2011-03-14

Should have a file_exists before include_once.
function __autoload($class)
{
if(strpos($class, 'CI_') !== 0)
{
@include_once( APPPATH . 'core/'. $class . EXT );
}
}

should be
function __autoload($class)
{
if(strpos($class, 'CI_') !== 0)
{
if ( file_exists( APPPATH . 'libraries/'. $class . EXT ) )
@include_once( APPPATH . 'libraries/'. $class . EXT );
}
}

Otherwise if you set log threshold = 1, your log file will fill up very fast (a lot of warnings of not found file for inclusion).

Great post

Gravatar
F

2011-03-22

For those who read this post:

your MY_Controller should be located also in the core folder,
else you'll get blank pages.

Gravatar
Tania

2011-03-23

This is a nice article..
Its very easy to understand ..
And this article is using to learn something about it..

c#, dot.net, php tutorial

Thanks a lot..!

Gravatar
Varadha

2011-03-26

Hi,

I am a beginner in code igniter. I have my controllers basic setup as discussed in this tutorial:
application/core/MY_Controller.php
-----------------------------------
[code]class MY_Controller extends CI_Controller {

function __construct(){
parent::__construct();
}

}[/code]

application/controllers/Admin_Controller.php
---------------------------------------------
[code]class Admin_Controller extends MY_Controller {

function __construct(){
parent::__construct();
$this->is_logged_in();
}

function is_logged_in()
{
$admin_logged_in = $this->session->userdata('admin_logged_in');
if(!isset($admin_logged_in) || $admin_logged_in != true)
{
$data['main_content'] = 'admin_login_view';
$this->load->view('includes/admin_template', $data);
}
}
}[/code]

application/controllers/admin.php
---------------------------------
[code]class Admin extends Admin_Controller {

function __construct()
{
parent::__construct();
}

function login()
{
$data['main_content'] = 'admin_login_view';
$this->load->view('includes/admin_template', $data);
}

function members_area()
{
$data['main_content'] = 'admin_welcome_view';
$this->load->view('includes/admin_template', $data);
}
}[/code]

It works fine with login credentials. If i access the members_area() without login, it just loads the welcome view. I have to include many number of functions in the admin controller but all should be accessible after login only. Should i verify the login session for each and every function? Is there any other way to solve this? I need help on this. Please guide me.

Regards
Varadha

Gravatar
Bruno

2011-03-28

I'm working on a CI 1.7.2 with PHP 5.1.2 and its not working because the Frontend_Controller isn't been loading from autoloader.php. It's just working if I include the file on the Controller like this:

@include_once( APPPATH . 'libraries/Frontend_Controller' . EXT );
class Blog extends Frontend_Controller {
}

Any idea?

Gravatar
Carlos Adrián Morales

2011-04-02

And now, I love CI a bit more

Gravatar
Sid

2011-04-10

Thanks again! I've seen the above methods in your PyroCMS code. Smart!

Gravatar
Spicer Matthews

2011-04-13

Such a cool hack. Why can't it make it into Reactor?

Gravatar

2011-04-13

Spicer: It's a methodology, not a hack, nor is it a feature. Basic autoloading of core and libraries would make this functionality work out the of box, but "base classes" are just an idea. :)

Gravatar
Thomas

2011-04-22

Why don't put all classes in the /application/core/MY_Controller.php file?

class MY_Controller extends CI_Controller

class Public_Controller extends MY_Controller

class Admin_Controller extends Public_Controller or
class Admin_Controller extends MY_Controller


In this case you don't need "hack" your config.php

Gravatar

2011-04-23

It's not a hack at all. Adding an autoload is a perfectly acceptable thing to have in a config file as how things are loaded is up to you. The "put all classes in the same file" approach is of course possible but not only is it messy and against the "one file one class" rule, but if these classes start to grow you have a lot of extra PHP kicking around thats not going to be used.

Why load Admin logic for frontend users?

Gravatar
Thomas

2011-04-25

Thx for the answer!

I think, to force the normal (CI) loading order is a hack.
CI advise that the Controller class is not a library, but a "core class", so put your Controller in the custom
library folder is not meet their "rules", and not too logical as well.
"Base Controller" to libraries, "Public Controller" to core files, "Admin Controller" to libraries and to hack the config file makes more mass than to put 3 absolutely coherent class to one file...

Who to load your Admin Controller for your admin users?

Sorry for my English, I think my PHP is better :)

Gravatar
Thomas

2011-04-25

Who to... = How to load :)

Gravatar

2011-04-26

This article was written before the core/ folder ever existed. The "rules" are nothing to do with core/ vrs libraries/ as this is just a logical separation to keep core extensions away from third-party Twitter libs, etc.

All they mean is that a Controller is not loaded through $this->load->library('controller') but is instead loaded via an include. This __autoload() actually works in the same was as MY_Controller is checked for and included, so actually this is perfectly suitable behaviour.

Gravatar
Anthoni Giskegjerde

2011-04-27

Hello,

Thanks for heads up about this snippet here. However, after using it I noticed the logs file fill up very fast. Have any idea why/ how to remove the errors?

Screenshot: http://cl.ly/6IBi

Cheers.

Gravatar
Mike Zens

2011-04-29

Love your blog posts. Great advice.

Gravatar
735

2011-05-19

I'm newbie in CodeIgniter,
I've followed the code, and I want to print/echo a string, but why I get blank page, what's wrong with this pseducode

class Blog extends Public_Controller
function index() {
echo "tsting";
}

Gravatar
Ghprod

2011-05-20

for all who get blanks page or error log .. dont forget to move My_Controller into application/core folder :)

not application/libraries anymore ..

btw Thanks a lot Phil :)

Gravatar
735

2011-05-24

ooow, I didn't notice it.
Thx to the Author & Ghprod
This is cool

Gravatar
David

2011-06-08

Quick question (you must love comments on very old posts).

if(strpos($class, 'CI_') !== 0)

prevents the autoloader trying to (re)load native CI classes/libraries, such as CI_Controller? Doesn't Codeigniter automatically load core/libraries that start with MY_ as well (assuming you haven't renamed the prefix), so MY_Controller, MY_Loader etc are all automatically loaded? As such, does it make sense to do

if(strpos($class, 'CI_') !== 0 && strpos($class, 'MY_') !== 0)

[according to my testing, that works fine, I'm just trying to check if I'm missing anything]

Gravatar
Phil Sturgeon

2011-06-08

David: That hack is to avoid some weirdness with how the database classes are loaded compared to others. As you said this post is old so may not happen in newer versions, but it should break if you remove this check and try to work with active record.

Gravatar
Marv

2011-06-23

I'm using versions 2.0.2 and I'm also having a problem with MY_controller on my web host. It's working fine on my local machine. I've added __autoload at the end of config.php but it's still not working. Help please?

Gravatar
Marv

2011-06-23

It's now working! The filename is MY_controller but the class name is MY_Controller so i just changed the filename.

Gravatar
Mike

2011-06-29

As Rafael pointed out earlier in thread, helps to check if class exists before trying to load it. In CI 2 you need to use 'core' instead of 'libraries'

like so...

function __autoload($class)
{
if(strpos($class, 'CI_') !== 0)
{
if ( file_exists( APPPATH . 'core/'. $class . EXT ) )
@include_once( APPPATH . 'core/'. $class . EXT );
}
}

Gravatar
Angelo

2011-07-24

Put a Base class in library, core or controller folder could affect the performance memory in which of them?

The framework Yii make use of autoload on its classes, thus the fastest framework, could we on codeigniter do the same?

thanks

Gravatar
Angelo

2011-07-24

I would like to know why in MY Model you mentioned above, has form_validation, is this the best way than in controller? What is the main advantage to use that class?

Gravatar
Ali Turab Gilani

2011-08-14

That is exactly how I work in JEE Servlets...!!! Perfecto for PHP!

Gravatar
Ironlung

2011-08-27

Absolutely awesome thanks - just what I needed!!!!

Gravatar
Andy Wright

2011-09-08

Awesome -- Really useful!

Gravatar
Gary Peach

2011-10-08

I've been trying to figure out a good way to share data between controllers for a couple of days, thanks Phil!

Gravatar
Roj

2011-11-10

Loving the general approach here, thanks! However, I would want to do it slightly differently — possibly saving some memory as both Admin_Controller & Public_Controller don’t need to be loaded & __autoload will do that.

Simply add a conditional at the beginning of MY_Controller.php.

<pre>
if ( isset( $URI->segments[1] ) && $URI->segments[1] === 'admin' )
{
include_once( APPPATH . 'core/Admin_Controller.php' );
}
else
{
include_once( APPPATH . 'core/Public_Controller.php' );
}

class MY_Controller extends CI_Controller {
// Continue as normal
</pre>

Just another option thrown in the mix.

Gravatar
Jeff Walters

2012-01-17

Phil, very helpful tutorial! I was looking for a way to setup custom workflows, which would extend from a common controller (params, methods, etc), but I wasn't sure how to do it with CodeIgniter. As always, you had the answer here on your blog. You were right on target on this one. Thanks, Jeff

Gravatar
Mr Dummy

2012-04-10

oh thanks phil, it work,itvery useful for me

Gravatar
Shane

2012-04-21

I don't think this is a good approach anymore. Codeigniter offers URI Routing. It is very easy to use and does the same thing. Here is their documentation

http://codeigniter.com/user_guide/general/routing.html

C.

Gravatar

2012-04-21

Shane: Thank you for your feedback but what you suggest is absolutely irrelevant. This has nothing to do with routing whatsoever.

Routing has been around since the early 1.x versions and is nothing new. It helps you "alias" URL's so that one URL will go to a different Controller/Method/Parameter order.

Base controllers are a way of combining logic for various areas within a site. I think you should probably read the article again.

Gravatar
Andreas Bergström

2012-05-21

Awesome, thanks! However I prefer to put the autoload-method in a custom config file &#40;preferably the current applications custom config file&#41; to keep original CodeIgniter nice and clean.

Gravatar
Yantar

2012-05-31

Great solution, thank you.
I searched, how better this do and found your article. Thanks.

Gravatar
Bruno

2012-06-10

Hey Phil, nice solution, i keep using it, but i'm building a project that i need some common functions, and i need to use a library for them and need to call the library "Common" but that gives me an error, because it tries to load "core/MY_Common.php" and the file is in "libraries/Common.php"

Do you have and advice to fix this ?

Thank you !

Gravatar
Yantar

2012-06-20

I improved partly your solution, when you need extend controller from another controller (but not from core folder).

function __autoload($class)&#123;
if(strpos($class, 'CI_') !== 0) &#123;
$paths = array(APPPATH . 'core/', APPPATH . 'controllers/');
foreach($paths as $path) &#123;
if (file_exists($path . $class . EXT)) &#123;
include_once( $path . $class . EXT );
break;
&#125;
&#125;
&#125;
&#125;

Gravatar
Windie

2012-06-20

Hi everyone

could you help me this error:


404 Page Not Found

The page you requested was not found.

I also did

MY_Controller.php located in application/core
class MY_Controller extends CI_Controller
&#123;
function __construct()
&#123;
parent::__construct();
&#125;
&#125;

welcome.php
class Welcome extends MY_Controller &#123;

function __construct()
&#123;
parent::__construct();
&#125;


and at the end of the config.php file
function __autoload($class)
&#123;
if(strpos($class, 'CI_') !== 0)
&#123;
@include_once( APPPATH . 'core/'. $class . EXT );
&#125;
&#125;


Do i need config something more.
Thank in advanced!

Gravatar
Windie

2012-06-21

Nvm
I've resolved it:
it needs function index() default for MY_Controller
Tx

Gravatar
Virgd

2012-07-01

Thanks Phil! Instead of _autoload would it be ok to just add for example require(APPPATH.'core/Public_Controller.php'); and other extending controllers in MY_Controller.php ?

Gravatar
Cheap Louis Vuitton Outlet

2012-07-10

great advice and discussing,I'll get this amazing for me .thanks!

Gravatar
Goyard Luggage

2012-07-11

This blog site is great. How did you come up witht he idea?

Gravatar
Burak Erdem

2012-07-15

Is this still possible with the latest version of CodeIgniter (which is 2.1.2 at the time)? I was happily using this method with my previous projects, but now I can't manage to get it work. It gives the following error;

Fatal error: Class 'Admin_Controller' not found in /sites/application/controllers/welcome.php on line 28

Posting comments after three months has been disabled.