How do you use multiple controllers in CodeIgniter

2019-02-18 06:31发布

问题:

I'm new to CodeIgniter and I've just gone through some of their user guide to help me understand how to do multiple controllers.

I have figured out how to load multiple pages using one of their examples. This is my default controller, called Site.php:

class Site extends CI_Controller {

public function index($page = 'home') {
    if ( ! file_exists(APPPATH.'/views/'.$page.'.php')) {
        // Whoops, we don't have a page for that!
        show_404();
    }

    $data['title'] = ucfirst($page);

    $this->load->view('header', $data);
    $this->load->view($page, $data);
    $this->load->view('footer', $data);

    }
}

This all works well and good with my routes.php:

$route['default_controller'] = 'site';
$route['(:any)'] = 'site/index/$1';

I have a few views that do load correctly when I go to localhost/website/index.php/about, for example.


Now, to further learn about controllers and URI routing. I created a new controller, application/controllers/MyController.php and it is coded as such:

class MyController extends CI_Controller {
    public function index() {
        $this->load->view('header');
        $this->load->view('my_controller');
        $this->load->view('footer');
    }
}

The thing is, I don't know how to access this page. I understand that the default URI pattern is example.com/class/function/id/ but I have tried localhost/website/mycontroller and it doesn't work. Apache returns 404. I've tried many manipulations of this, even going as stupid as typing localhost/website/index.php/mycontroller but of course that doesn't work.


What is the correct way to use multiple controllers? What have I done wrong here? Please assist me in my learning, thank you!

(Also, this is my first proper question on StackOverflow, if I've done anything wrong or formatted something incorrectly, please let me know!)

回答1:

The problem is that this rule:

$route['(:any)'] = 'site/index/$1';

intercepts everything... and passes it to the Site controller, as an argument to the index method. So if you call:

/mycontroller

it will actually map to:

/site/index/mycontroller

The routing happens before the app even looks at the controllers, and the routing rules are considered in order they are written.

Thus you need to put this rule at the very bottom of your rule list in order to let the other rules work. So by adding this in front:

$route['mycontroller'] = 'mycontroller';
$route['(:any)'] = 'site/index/$1';

it should work fine (although sligthly unusual approach, but so is your global any rule) as it will first check if the URL requested was /mycontroller and if so, it will call myController; otherwise it will behave like it used to with your Site controller.



回答2:

You are routing everything to your Site controller with the routing rule:

$route['(:any)'] = 'site/index/$1';

With such a catch-all routing rule you will never reach other controllers as for example your Mycontroller.



回答3:

The problem is your calling method In your case if you don't have mod_rewrite on you should try

localhost/website/index.php/mycontroller

if you are able to activate mod_rewrite you can add in your .htaccess the following lines:

RewriteEngine On
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^(.*)$ index.php/$1

after that you can call your controller like you tried before