0

I have a main class which initializes another class in a function of main class and I need to get a variable (in this case $this->db) from the main class to that another class. For example, I have a main class Wordle_Admin:

class Wordle_Admin
{
   public function __construct()
   {
       $this->db = new mysqli(DB_HOST, DB_USER, DB_PASSWORD, DB_NAME);
   }

   public function views()
   {
       include 'Wordle_Admin_Views.php';
       $wsa = new Wordle_Admin_Views();
       $view = @$_GET['view'];
       $id = @$_GET['id'];
       $type = @$_GET['type'];
       $action = @$_GET['action'];
       $msg = @$_GET['msg'];

       if( !empty( $view ) && method_exists( $wsa, $view ) ):
           $wsa::$view($id, $type, $action, $msg);
       elseif( !empty( $view ) && !method_exists( $wsa, $view ) ):
           echo'View does not exist.';
       else:
           $wsa::index($id, $type, $action, $msg);
       endif;
   }    

}

And I have another class:

class Wordle_Admin_Views extends Wordle_Admin
{
    public function __construct()
    {
        parent::__construct();
    }

    public function index( $id = "", $type = "", $action = "", $msg = "" )
    {
        $this->db->query('SELECT * FROM wordle_post');
    }
}

I can not use $this->db in Wordle_Admin_Views, it returns:

Fatal error: Using $this when not in object context in C:\Server\wordle\w-includes\Wordle_Admin_Views.php on line 22

So my question is, how can I pass a variable from parent class to class? All kind of help is appreciated, pointers on what to do differently are also accepted with open hands.

2
  • 4
    Using $this when not in object context has nothing to do with parents or children. It means you're using $this in a function that's called statically, or outside an object. How are you calling these functions? Commented Nov 28, 2011 at 22:50
  • I use Wordle_Admin::views() in a layout file (as in what user sees) to output pages that operate as functions (Wordle_Admin_Views's functions). My goal is to be able to use mysqli in Wordle_Admin_Views without initializing a new connection and instead using the connection that was initialized in Wordle_Admin. If that is possible, that is. Commented Nov 28, 2011 at 22:56

3 Answers 3

1

Your concrete problem is that you're calling the method statically. You don't have an object in a static context, so you can't use $this.

Your other problem seems to be that you're slightly misunderstanding inheritance. Since the DB connection is only created when you instantiate an object (new Worlde_Admin), the same goes for the child.

A Wordle_Admin_Views does not automatically have access to a DB connection that may or may not have been created in some instance of Worlde_Admin. Only that Worlde_Admin instance has that DB connection. You need to instantiate a Wordle_Admin_Views so it will have a connection as well (because it inherited the methods how to do so from Worlde_Admin).

$admin  = new Worlde_Admin;  // $admin now has its own db connection
$admin2 = new Worlde_Admin;  // $admin2 now has another db connection
$view   = new Wordle_Admin_Views;  // $view has yet another connection

Wordle_Admin_Views::index();  // this has no db connection

You should be looking into Dependency Injection, which means you create one mysqli instance outside your classes and inject that into each one when it is instantiated.

$db = new mysqli(...);

$admin = new Worlde_Admin($db);
$view  = new Wordle_Admin_Views($db);
Sign up to request clarification or add additional context in comments.

1 Comment

First of all, a lovely answer. This solution works like a charm.
0

It seems to me that this might be a part of issue:

   include 'Wordle_Admin_Views.php';
   $wsa = new Wordle_Admin_Views();

   /* blah blah */

   if( !empty( $view ) && method_exists( $wsa, $view ) ):
       $wsa::$view($id, $type, $action, $msg);
   elseif( !empty( $view ) && !method_exists( $wsa, $view ) ):
       echo'View does not exist.';
   else:
       $wsa::index($id, $type, $action, $msg);
   endif;

You are trying to access static function not on a class name but on object. It should be either Wordle_Admin_Views::$view() or $wsa->$view().

Have you actually learned php or are you pretending that it is some other language (python ?) and just "winging it".

5 Comments

Calling a static method or property on an object instance is actually an allowed shortcut. Not that it's necessarily a good idea, of course.
@deceze , i think he was doing it other way around: calling a normal method as static ( with $this used inside that method ).
It fixed the problem I had , thank you. As for have I learned; no, I have not. However I am learning. Also no, am not pretending as I don't really know any other language. I'm here to learn because for me it seems that learning from other's mistakes is the best way. As for motivation, I actually like a harsh word every now and then. It keeps the spirit alive and reminds me that I'm nowhere near where I want to be. So double thanks for that.
Which is why I answered in my downvoted way. Nothing in the class declared it as static, so calling it with :: would yield the same results. So I thought.
@KaiQing , yeah , that was the first thought , but testing it in codepad.viper-7.com indicated that undeclared class variables are not set as private.
0

in your world admin class try this...

class Wordle_Admin
{
    protected $db;

}

then your db var should be inherited when you call $this->db, assuming $this->db was defined in the parent class.

10 Comments

I'm guessing this was downvoted because, while it addresses what the OP says is the problem, it doesn't solve the actual problem (inferred from comments and the nature of the error message).
Did I misread something? declaring protected $db in the parent class makes $db visible to classes extending that controller. In the child controller you can call $this->db and it will return the parent $db if instantiated. Was that not the question?
@phoenix - really? he said this "I need to get a variable (in this case $this->db) from the main class to that another class." not WHY it wasn't working. He asked how to get it to work.
You could be right. I didn't downvote your answer; just curious if there might be a way to improve it to get it some upvotes.
@Kai If the property is not specifically declared as private in the parent, it absolutely does not matter whether it is declared at all. See codepad.org/6zjeEeZz
|

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.