Does CodeIgniter have to load view in the final step?
I have a function
function do_som开发者_StackOverflow社区ething() {
// process
$this->load->view('some_view', $data);
exec('mv /path/to/folder1/*.mp3 /path/to/folder2/');
}
My intention is to move files after outputting the view. But apparently it is done before rendering the view. My question is, does $this->load->view();
have to be the final step in a function?
I did a little research, and seems like my question is similar to this topic. Correct?
Why don't you just use a post_system
hook? It's called after the final page is sent to the browser, that way you can load views normally, without echoing them out.
Here's an example controller:
class Home extends Controller {
function index()
{
$this->move_audio = TRUE;
$this->old_folder = "/path/to/folder/";
$this->new_folder = "/path/to/folder2/";
$this->load->view("some_view");
}
}
And an example hook:
function post_system()
{
$CI =& get_instance();
if( isset($CI->move_audio) && $CI->move_audio === TRUE)
{
// Trim, then add trailing slash for consitency
$old_folder = rtrim($CI->old_folder, "/")."/*.mp3";
$new_folder = rtrim($CI->new_folder, "/")."/";
exec("mv {$old_folder} {$new_folder}");
}
}
Check out the hooks user guide for info on setting them up. They are your friends!
EDIT: Something I just thought of...
If you're only going to be doing this inside one controller method... it would probably be better to use Phil's approach. This would avoid having a hook call for every request which would be unnecessary if you only need it once.
Another thing you could do, if you only need it once, is use CI's _output()
handler for Controllers (info here). That would work like this:
class Home extends Controller {
// Initalize the var to avoid having to
// check if it's set or not
var $move_audio = FALSE;
// CONTROLLER METHOD
function index()
{
$this->move_audio = TRUE;
$this->old_folder = "/path/to/folder/";
$this->new_folder = "/path/to/folder2/";
$this->load->view("some_view");
}
// OUTPUT HANDLER
function _output($output = "")
{
echo $output;
if($this->move_audio === TRUE)
{
// Trim, then add trailing slash for consitency
$old_folder = rtrim($this->old_folder, "/")."/*.mp3";
$new_folder = rtrim($this->new_folder, "/")."/";
exec("mv {$old_folder} {$new_folder}");
}
}
}
Send the output to the browser before you run the command:
function do_something()
{
// process
echo $this->load->view('some_view', $data, TRUE);
exec('mv /path/to/folder1/*.mp3 /path/to/folder2/');
}
Otherwise you are just giving data to the Output class that will run as soon as the Controller is finished.
No. Actually for some web services I have just used something like this:
function get_json_search() {
$results = $this->My_model->get_stuffs();
echo json_encode($results);
}
You can also have controller functions which are fully private from the web. Just prefix them with '_'. You would never view these as pages.
function _upload_photo($filepath) { //resize it and so on
Perhaps you are misunderstanding MVC. The controller is an intermediary between the model and view. Likewise you don't need to use models either. The controller just getting stuff from models and using the view to print it out. There is no reason (although it would be bad style) you cannot use data from within the controller or from other sources or print out your page from the controller.
I don't see why it won't work if you load the view first. Although I would do it the other way around so you can offer feedback to the user. You should display an error to them if the files fail to move. If it is performance intensive consider using a queue or cron jobs.
<?php
while (ob_get_level()) {
ob_end_flush();
}
// start output buffering
if (ob_get_length() === false) {
ob_start();
}
class Something extends Controller {
function do_something() {
$this->load->view('some_view', $data);
ob_flush(); flush();
exec('mv /path/to/folder1/*.mp3 /path/to/folder2/');
}
}
?>
精彩评论