Welcome Guest, Not a member yet? Register   Sign In
Models and controllers classes member variables issues
#1

[eluser]Unknown[/eluser]
Hi, I'm having a strange behaviour using a model within a controller, I'm not much familiar with CI development, I just started from a few weeks, anyway, my problem is that model instance somehow considers the variables declared in the controller class as member class of his own instance and then it tries to produce SQL code according to this, needless to say this cause an error since my model table doesn't contain this row.

As example:
Code:
class Foo extends Controller
{
    var $fooInFoo = '';

    function Foo()
    {
        parent::Controller();
        $this->fooInFoo = "Hello from foo";
    }

    function index()
    {
        echo "<pre>";
        $this->load->model('MyModel');

        echo $this->fooInFoo;
        echo "\n";
        echo $this->MyModel->fooInMyModel;
        echo "\n";

        print_r($this->MyModel);

        echo "</pre>";
    }
}

class MyModel extends Model
{
    var $fooInMyModel = '';

    function MyModel()
    {
        parent::Model();

        $this->fooInMyModel = "Hello, from modelfoo!";
    }

    function insert()
    {
        $this->db->insert('foo_table', $this);
    }
}

... and this is the output ...
Code:
Hello from foo
Hello, from modelfoo!
MyModel Object
(
    [fooInMyModel] => Hello, from modelfoo!
    [_parent_name] => MyModel
    [fooInFoo] => Hello from foo
    [_ci_scaffolding] =>
    [_ci_scaff_table] =>
    [config] => CI_Config Object
        (
.... etc ....

If I declare controller member variable as private this don't happen, btw this is not compatible with PHP < 5.
Is this considered normal or am I taking a wrong direction using models and controller?

thx for the replies.
#2

[eluser]danmontgomery[/eluser]
You really shouldn't be directly inserting the model using $this, if you're looking to directly relate models to database tables you should look at an ORM like DMZ or Doctrine.
#3

[eluser]JoostV[/eluser]
Prepend your class variables with an underscore to make them private. See userguide

Code:
var $_fooInMyModel = '';

Or, just use good old PHP5 Smile
Code:
private $_fooInMyModel = '';
#4

[eluser]Unknown[/eluser]
Sad uhmm, unfortunately the underscore method doesn't work

Code:
INSERT INTO `foo_table` (`_fooInMyModel`, `fooInFoo`) VALUES ('Hello, from modelfoo!', 'Hello from foo')
#5

[eluser]danmontgomery[/eluser]
Prepending variables with _ doesn't make them private. It's used as an indicator in PHP4 that they should be considered private variables, since PHP4 doesn't support public/private/protected.

This will happen with any variables declared before the model is loaded, when any model is loaded it calls _assign_libraries.

Code:
function _assign_libraries($use_reference = TRUE)
    {
        $CI =& get_instance();                
        foreach (array_keys(get_object_vars($CI)) as $key)
        {
            if ( ! isset($this->$key) AND $key != $this->_parent_name)
            {            
                // In some cases using references can cause
                // problems so we'll conditionally use them
                if ($use_reference == TRUE)
                {
                    $this->$key = NULL; // Needed to prevent reference errors with some configurations
                    $this->$key =& $CI->$key;
                }
                else
                {
                    $this->$key = $CI->$key;
                }
            }
        }        
    }

Again, you shouldn't be directly inserting a model without checking the fields you're inserting. You should really be using an ORM like DMZ or Doctrine.




Theme © iAndrew 2016 - Forum software by © MyBB