kostenloser Webspace werbefrei: lima-city


Fatal error....

lima-cityForumProgrammiersprachenPHP, MySQL & .htaccess

  1. Autor dieses Themas

    testworld

    testworld hat kostenlosen Webspace.

    Hallo,

    Ich teste mich gerade an OOP und plötzlich tauchte eine Fehlermeldung auf:
    Fatal error: Call to a member function query() on a non-object in /var/www/.../.../.../class/login.php on line 25

    Der gesamte Code besteht zurzeit zwar noch aus vielen Fehlern, die ich aber zurzeit abarbeite, weil ich bisher noch nichts in der Praxis getestet habe.

    Der Code sieht folgendermaßen aus:
    <?php
    	
    	class login 
    	{
    		public $name;
    		public $passwort;
    		public $ID;
    		public $IP;
      
    		public function __construct()
    		{
    		$DB = new db('localhost','...','...','...');
    		
    		if (!isset($_POST['login']) AND !isset($_POST['username']))
    		{
     
    			$this -> name = $_POST['username'];
    			$this -> passwort = $_POST['passwort'];
    			return true;
    		}
    
    		}
    	
    		public  function login()
    		{  
    			$DB -> query('SELECT * 
    			   FROM user
    			  WHERE  
    			   name     = \''. mysql_real_escape_string($this -> name) .'\' AND
    			   passwort = \''. mysql_real_escape_string(MD5($this -> passwort)) .'\'
    			  LIMIT 1;');
    			$row = $DB -> count();
    			if($DB -> count()!=1)
    			{
    				return false;
    			} 
    			else 
    			{
    				$row = $DB -> fetchRow();
    				$this -> ID = $row['ID'];
    				$_SESSION['airport'] = new Airport($this -> ID);
    				$_SESSION['user'] = new User($this -> ID);
    				
    				$query = 'UPDATE  
    			           user
    			          SET  
    			           IP = \''. mysql_real_escape_string($this -> IP) .'\' 
    			          WHERE 
    			           ID =  '. $this -> ID .' 
    			          LIMIT 1;';
     
    				$DB -> query();	
    				return true;
    			}
    		}
    	}
    
    ?>


    Weiß einer wie ich den Fehler beheben kann?


    EDIT:
    Also ich habe jetzt eine temproale Lösung gefunden: Einfach die DB Verbdinung in der Funktion nochmal herstellen, aber ich frage mich wieso es so nicht eght, weil im Konstruktor doch eigt. schon eine Verbindung hergestellt wird?!

    Beitrag zuletzt geändert: 9.7.2011 0:19:05 von testworld
  2. Diskutiere mit und stelle Fragen: Jetzt kostenlos anmelden!

    lima-city: Gratis werbefreier Webspace für deine eigene Homepage

  3. testworld schrieb:
    ... Fatal error: Call to a member function query() on a non-object in /var/www/.../.../.../class/login.php on line 25
    ...
    besagt genau das, was sache ist:
    deine 'db' class wird in der zeile
    <?php
    ...
    		$DB = new db('localhost','...','...','...');
    ...
    nicht instanziiert und ein 'nicht'instanz kann natürlich keine methoden enthalten.

    ich würde es so lösen (allerding trotz funktionalität eher schematisch [schulzweck]):
    <?php
    
    define('DEVEL', (bool)1);
    define('TOSTRG', (bool)1);
    
    
    echo $login = new CLogin();
    
    // database user name/password
    class CDbUser {
      public $db_user      = '...';
      public $db_user_pwd  = '...';
    }
    
    // database class
    class CDb extends CDbUser {
      public $db_host  = '...';  // 'localhost' ...?
      public $db_conn  = null;
      public $db_error = null;
      public $db_count = null;
    
      public function __construct() {
        $this->db_conn = ($c = mysql_connect($this->db_host, $this->db_user, $this->db_user_pwd)) ?
          $c:
          $this->db_error();
      }
    
      public function query() {
        // ... ;
      }
    
      public function db_count() {
        // ... ;
      }
    
      public function __destruct() {
        if(is_resource($this->db_conn)) {
          mysql_close($this->db_conn);
        }
      }
    
      public function db_error() {
        $en = mysql_errno();
        $et = mysql_error();
    
        if(!DEVEL) {
          $this->db_error = array($en, $et);
          return;
        }
    
        echo <<< EOT
    <!DOCTYPE html>
    <html>
      <head><title>db_error</title></head>
      <body>
        <h3>db error:</h3>
        <pre>
          #          : $en
          description: $et
        </pre>
      </body>
    </html>
    EOT;
      }
    
    }
    
    // login class
    class CLogin extends CDb {
      public $name;
      public $passwort;
      public $ID;
      public $IP;
      
      public function __construct() {
        CDb::__construct();
    		
        if (!empty($_POST['login']) AND !empty($_POST['username'])) {
          $this->name     = $_POST['username'];
          $this->passwort = $_POST['passwort'];
          return true;
        }
      }
    	
      public  function login() {
        $DB -> query('SELECT * 
          FROM user
          WHERE  
            name     = \''. mysql_real_escape_string($this -> name) .'\' AND
            passwort = \''. mysql_real_escape_string(MD5($this -> passwort)) .'\'
          LIMIT 1;');
        $row = $DB -> count();
        if($DB -> count()!=1) {
          return false;
        } else {
          $row = $DB -> fetchRow();
          $this -> ID = $row['ID'];
          $_SESSION['airport'] = new Airport($this -> ID);
          $_SESSION['user'] = new User($this -> ID);
    				
          $query = 'UPDATE  
              user
            SET  
              IP = \''. mysql_real_escape_string($this -> IP) .'\' 
            WHERE 
              ID =  '. $this -> ID .' 
            LIMIT 1;';
     
          $DB -> query();	
          return true;
        }
      }
    
      public function __toString() {
        return (!TOSTRG) ? '': '<pre>' . print_r($this, true) . '</pre>';
      }
    
    }
    wobei in der login class müssen alle 'DB->...' angepasset werden ($this->query(), ...). (ich weiß, ich bin ein faulsack ;o)

    ausserdem, richtige daten ('...') musst du editieren
    und zum schluss: so einen class 'CDbUser' würde ich aus sicherheitsgründen nicht so einsetzen. aber es geht ja doch nur um OOP prinzip.

    lg

    Beitrag zuletzt geändert: 9.7.2011 3:14:20 von hemiolos
  4. Ich versteh deinen Post nicht wirklich... Kannst du mit vielleicht den Code nochmal erklären?
    Bzw. gibt es auch andere Möglichkeiten?

    Beitrag zuletzt geändert: 9.7.2011 9:44:15 von volnerius
  5. Zu deinem Problem kann man eben nur sagen, dass $DB kein Objekt ist. Ich sehe auch keine Klasse db in deinem Code, die diese Funktion query besitzt.

    Setze einfach mal das ein:
    $DB = new db('localhost','...','...','...');
    var_dump( $DB );


    Ich wette da kommt "null" zurück und null ist kein Objekt und kann deshalb auch keine Funktionen enthalten bzw. ausführen.
  6. Dann frage ich mich, aber immernoch wieso es nicht funktioniert wenn die Vebrindung im Konstruktor erstellt wird, aber direkt in der Funktion schon?!

    Beitrag zuletzt geändert: 9.7.2011 10:34:21 von volnerius
  7. Achso entschuldige habe den Edit nicht gesehn und den Fehler übersehn. Das hängt einfach damit zusammen, dass $DB nur lokal ist. Nachdem Ende des Konstruktors wird sie gelöscht.
    Wenn du diese weiter in dem Objekt verwenden willst musst du sie als Klassenattribut deklarieren und mit $this->DB darauf zugreifen.

    So:
    <?php
    	class login 
    	{
                    private $DB;
    		public $name;
    		public $passwort;
    		public $ID;
    		public $IP;
      
    		public function __construct()
    		{
    		$this->DB = new db('localhost','...','...','...');
    		
    		if (!isset($_POST['login']) AND !isset($_POST['username']))
    		{
     
    			$this -> name = $_POST['username'];
    			$this -> passwort = $_POST['passwort'];
    			return true;
    		}
    
    		}
    	
    		public  function login()
    		{  
    			$this->DB -> query('SELECT * 
    			   FROM user
    			  WHERE  
    			   name     = \''. mysql_real_escape_string($this -> name) .'\' AND
    			   passwort = \''. mysql_real_escape_string(MD5($this -> passwort)) .'\'
    			  LIMIT 1;');
    			$row = $this->DB -> count();
    			if($this->DB -> count()!=1)
    			{
    				return false;
    			} 
    			else 
    			{
    				$row = $this->DB -> fetchRow();
    				$this -> ID = $row['ID'];
    				$_SESSION['airport'] = new Airport($this -> ID);
    				$_SESSION['user'] = new User($this -> ID);
    				
    				$query = 'UPDATE  
    			           user
    			          SET  
    			           IP = \''. mysql_real_escape_string($this -> IP) .'\' 
    			          WHERE 
    			           ID =  '. $this -> ID .' 
    			          LIMIT 1;';
     
    				$this->DB -> query();	
    				return true;
    			}
    		}
    	}


    Tipp: Ich würde sie static machen. Damit würde für alle Login nur eine Datenbankverbindung aufgebaut werden. Du kansnt dann eben mit self::$DB darauf zugreifen.

    Beitrag zuletzt geändert: 9.7.2011 10:24:45 von reimann
  8. Diskutiere mit und stelle Fragen: Jetzt kostenlos anmelden!

    lima-city: Gratis werbefreier Webspace für deine eigene Homepage

Dir gefällt dieses Thema?

Über lima-city

Login zum Webhosting ohne Werbung!