CodeIgniter - Two Forms, One Page

2019-09-16 04:49发布

I'm having a fundamental problem in understanding the concept of MVC and displaying more than one form at a time. I've tried a variety of methods but I'm still stuck - and that's because I don't think I'm understanding CI and MVC correctly.

I tried using 2 different views for the two different forms. Didn't work. I tried using one function per form in my controller. That didn't work either. I don't know what to do.

Should I be doing this;

  1. Create a controller and have an index() function in it.
  2. Build up my form elements for each form within this index()
  3. Create 1 view that displays both forms and call it from within index()
  4. Use form_open to direct the submit action to another function - call it validate()
  5. Validate everything that comes in, send back errors
  6. Somehow, and this is the main bit I don't get, complete an action if the form has been filled in correctly.

6 Is my biggest problem. Don't know how to do that. For example, on successful completion of the form I want my user to have created a directory at a chosen location - so I'm using mkdir() - so do I need an if statement within the validate() function or what??

UPDATE

Here is the code I have created so far;

Controller:

<?php if ( ! defined('BASEPATH')) exit('No direct script access allowed');

// Forms CodeIgniter controller class Admin extends CI_Controller {

// Controller constructor
public function __construct()
{
    parent::__construct();
    // Load form helper required to validate forms
    $this->load->helper(array('form', 'url'));
    $this->load->library('form_validation');        
}

//*************************************************//

// Prepare data for the view to output the forms
public function index()
{

    //*****************************************************//
    //returns a drop down list of radio buttons, one for each directory
    $map_one = $this->recursive_model->iterate_add_folder_names();
    $data['folder_list_add'] = $map_one;    
    //****************************************************//
    //*****************************************************//
    //also returns a drop down list of radio buttons (slightly different), one for each directory
    $map_two = $this->recursive_model->iterate_folder_names();
    $data['folder_list_select'] = $map_two; 
    //****************************************************//

    //load the views and the forms
    $this->load->view('templates/header.php');
    $this->load->view('admin/add_new_folder.php', $data);
    $this->load->view('admin/add_new_file.php', $data);
    $this->load->view('templates/small_footer.php');
}

//*************************************************//

//function if adding a new directory to the current structure
public function add_folder()
{
    //need to select a directory for it to go under
    $this->form_validation->set_rules('new_folder', 'New Folder', 'required');
    //and name the new directory
    $this->form_validation->set_rules('new_folder_name', 'New Folder Name', 'required');

    if ($this->form_validation->run() === FALSE)
    {
        $this->index();
    }
    else
    {   
        if($this->input->post())
        {
            $new_folder = $this->input->post('new_folder');
            $new_folder_name = $this->input->post('new_folder_name');
            $folder_path = "/var/www/html/mike/content".$new_folder."/".$new_folder_name;
            mkdir($folder_path, 0777);
            $this->index();
        }
    }

}

//*************************************************//

public function add_file()
{

    //folder location and name of file
    $folder_name = $this->input->post('folder_name');
    $new_folder_name = $this->input->post('file_name');

    //validation rules
    $this->form_validation->set_rules('folder_name', 'Folder Name', 'required');
    $this->form_validation->set_rules('file_name', 'File Name', 'required');

    //if there is an error with validation
    if ($this->form_validation->run() === FALSE)
    {
        //gets stuck here every time when trying to upload a new folder :(
        $this->index();
    }
    //if there is not an error with validation
    else
    {   
        //$folder_name will be something like "http://www.example.com/publications/people/reports"
        $config['upload_path'] = $folder_name;
        $config['allowed_types'] = 'gif|jpg|png|html|pdf|xls';
        $this->load->library('upload', $config);

        //if file cannot be loaded (due to $config perhaps?)
        if ( ! $this->upload->do_upload())
        {
            $error = array('error' => $this->upload->display_errors());
            $this->index();
        }
        else
        {
            $data = array('upload_data' => $this->upload->data());
            $this->index();
        }

    }   

}

//*************************************************//

}

Here is one view (add_new_file.php);

<div id="container">

<h1>Upload A File/Publication</h1>

<div id="body">

<?php //echo $error;?>

<?php echo form_open_multipart('admin/add_file');?>

<?php echo $folder_list_select; ?>   &nbsp;&nbsp; 
<input type="file" name="file_name" size="20" />   &nbsp;&nbsp; 
<input type="submit" value="upload" />

</form>

</div>

Here is the other (add_new_folder.php)

div id="container">

<h1>Add A New Folder</h1>

<div id="body">

<?php echo validation_errors(); ?>

<?php echo form_open('admin/add_folder');?>

<?php echo $folder_list_add; ?>   &nbsp;&nbsp; 
New Folder Name: <input type="text" name="new_folder_name">   &nbsp;&nbsp; 
<input type="submit" value="upload" />

</form>

</div>

I hope this helps answer this thread.

Basically, I can get the first section to work - adding a folder - but I cannot get the adding a file to work. This is because if ($this->form_validation->run() === FALSE) is always returning false. I think it might be looking at the form elements in the other form - which it shouldn't do. What am I missing?

1条回答
虎瘦雄心在
2楼-- · 2019-09-16 05:12

Should I be doing this;
1 . Create a controller and have an index() function in it.
[let's, for the sake of conversation, call this controller Users thx -ed]

Sure. That's cool. You could also have a function in that Controller called edit, or banana or whatever; either way works. With using just the index method (function), the url might look like http://example.com/index.php/users whereas if you add another method to the controller like banana, the url might look like http://example.com/index.php/users/banana.

2 . Build up my form elements for each form within this index()

Well, typically form elements are not created in the controllers. This is where the V in MVC comes in -- stuff you view goes into a view.

So, one might do something like

// Users Controller
class Users extends CI_Controller{
    function index(){
        //index method
    }

    function banana(){
        $this->load->view('banana_view');
    }
}

then in application/views/banana_view.php, you create your form. When you visit http://example.com/users/banana, you will see the form you created in banana_view.php.

3 . Create 1 view that displays both forms and call it from within index()

Sure, that'd work just fine. But remember that each <form></form> needs its own <input type="submit" name="Lets GO"> inside and thusly needs somewhere to send each forms data. This is the action="". You can leave it out, but beware that it will then send the form to whatever page you are currently on (in our case here, http://example.com/index.php/users/banana), so you have to have something in the banana() method to handle the form data. But, typically, it will be set via form_open(). Something like form_open('index.php/users/eat_banana'); will generate <form action="index.php/users/eat_banana"...

4 . Use form_open to direct the submit action to another function - call it validate()

Just don't call it late_for_dinner. But seriously, validate is a bit broad -- validate what? Validate why? As to validation, https://www.codeigniter.com/user_guide/libraries/form_validation.html. But you should cross that bridge after you grok the fundamentals of CodeIgniter (won't take long).

5 . Validate everything that comes in, send back errors

See last question.

6 . Somehow, and this is the main bit I don't get, complete an action if the form has been filled in correctly.

Many times people will display a success message

class Users extends CI_Controller{

    function index(){
        //index method
    }

    function banana(){
        $this->load->view('banana_view');
    }

    // assuming form_open('index.php/users/eat_banana'); in banana_view
    function eat_banana(){
        //make sure that this is a POST
        if($this->input->post()){
            // do things with the data
            // typically it gets saved to a database
            // via a model (the M in MVC)
            // http://ellislab.com/codeigniter/user-guide/general/models.html

            if($saved_to_db){
                // set message to send to the view
                $data['message'] = "Everything went OK";
            }else{
                $data['message'] = "but who was database? data didn't save :(";
            }
            // load the view and send the data
            $this->load->view('eat_banana', $data);
        }
     }

application/views/eat_banana.php:

 <!DOCTYPE html>
 <html>
 <head></head>
 <body>
 <div>
     <b>Form submitted.</b><br />
     The message is: <?php echo $message; ?>
 </div>
 </html>

other times, one might instead prefer to redirect

class Users extends CI_Controller{

    function index(){
        //index method
    }

    function banana(){
        $this->load->view('banana_view');
    }

    // assuming form_open('index.php/users/eat_banana'); in banana_view
    function eat_banana(){
        //make sure that this is a POST
        if($this->input->post()){
            // do things with the data             
            if($saved_to_db){
                // just send them to the homepage
                redirect('/');
            }else{
                // send them back to the form
                redirect('index.php/users/banana');
            }
        }
     }

So,

M is for model. Models are used to talk to the database.

V is for Vend view. Views render the text, forms, pictures, gifs, whatever to the screen. That's the idea anyway. There's nothing stopping you from echo'ing out an enormous unminimized javascript application from your controller. That would totally not be MVC tho.

C is for controller. Controllers call and send data to the views, receive data sent from views, take that data and send it to a model to be saved in the database (although CodeIgniter doesn't enforce this in any way either; you could if you wanted to save the data to a database directly from the controller, but this obviously defeats the MVC principal as well), retrieves data from the database and sends it to a view for display. Those are the basics anyway.

查看更多
登录 后发表回答