Achot: Fatal error: Call to a member function

Guten Morgen,

ich komme mal wieder nicht weiter.

function bestandNachEingabe($mysqli, $Eingabe=false){
        
    if ($Eingabe) {

        $sql = "SELECT SUM(bestand) AS `summeBestand`, titel 
                  FROM artikel WHERE MATCH(`titel`) AGAINST(? IN BOOLEAN MODE) ";
        $res->bind_param("s", $Eingabe);
            
    }
        
    else {

        $sql = "SELECT SUM(bestand) AS `summeBestand` FROM artikel";

    }
        
    $res = $mysqli->prepare($sql);
    $res->execute();
    $res->bind_result($summeBestand);
    $res->fetch();
    $res->close();  

    return $summeBestand; 
}

Wenn ich diese Funktion aufrufe, erhalte ich folgende Fehlermeldungen

Notice: Undefined variable: res in line 8
Fatal error: Call to a member function bind_param() on a non-object

Was mache ich falsch?

  1. Hallo

    function bestandNachEingabe($mysqli, $Eingabe=false){
            
        if ($Eingabe) {
    
            $sql = "SELECT SUM(bestand) AS `summeBestand`, titel 
                      FROM artikel WHERE MATCH(`titel`) AGAINST(? IN BOOLEAN MODE) ";
            $res->bind_param("s", $Eingabe);
                
        }
            
        else {
    
            $sql = "SELECT SUM(bestand) AS `summeBestand` FROM artikel";
    
        }
            
        $res = $mysqli->prepare($sql);
        $res->execute();
        $res->bind_result($summeBestand);
        $res->fetch();
        $res->close();  
    
        return $summeBestand; 
    }
    

    Notice: Undefined variable: res in line 8
    Fatal error: Call to a member function bind_param() on a non-object

    Was mache ich falsch?

    Ich hab's zwar nicht so mit objektorientierter Programmierung, aber hier sieht es eindeutig aus. Das Objekt $res ist in der Funktion nicht bekannt.

    Tschö, Auge

    --
    Wenn man ausreichende Vorsichtsmaßnahmen trifft, muss man keine Vorsichtsmaßnahmen mehr treffen.
    Toller Dampf voraus von Terry Pratchett
    1. Hallo,

      klar, es muss ja auch so lauten :/

      function bestandNachEingabe($mysqli, $Eingabe=false){
              
          if ($Eingabe) {
      
              $sql = "SELECT SUM(bestand) AS `summeBestand`, titel 
                        FROM artikel WHERE MATCH(`titel`) AGAINST(? IN BOOLEAN MODE) ";
              $res = $mysqli->prepare($sql);
              $res->bind_param("s", $Eingabe);
                  
          }
              
          else {
      
              $sql = "SELECT SUM(bestand) AS `summeBestand` FROM artikel";
              $res = $mysqli->prepare($sql);
      
          }
          $res->execute();
          $res->bind_result($summeBestand);
          $res->fetch();
          $res->close();  
      
          return $summeBestand; 
      }
      

      Jetzt sind zwar die Fehler weg, allerdings bekomme ich auch kein Ergebnis.

      EDIT: Im $res->bind_result hat §titel gefehlt. Jetzt zeigt SUM auch das richtige Ergebnis an. Danke für die Hilfe.

      1. Hallo

        function bestandNachEingabe($mysqli, $Eingabe=false){
            if ($Eingabe) {
                $sql = "SELECT SUM(bestand) AS `summeBestand`, titel 
                          FROM artikel WHERE MATCH(`titel`) AGAINST(? IN BOOLEAN MODE) ";
                $res = $mysqli->prepare($sql);
                $res->bind_param("s", $Eingabe);
            }
            else {
                $sql = "SELECT SUM(bestand) AS `summeBestand` FROM artikel";
                $res = $mysqli->prepare($sql);
            }
            $res->execute();
            $res->bind_result($summeBestand);
            $res->fetch();
            $res->close();  
            return $summeBestand; 
        }
        

        Jetzt sind zwar die Fehler weg, allerdings bekomme ich auch kein Ergebnis.

        Prüfe mit Kontrollausgaben, ob der Query aussieht, wie er aussehen soll. Zudem hast du keine Fehlerbehandlung. Wenn einer deiner Queries wegen eines Fehlers nicht ausgeführt wird, erfährst du ohne Fehlerausgabe nichts relevantes darüber.

        Tschö, Auge

        --
        Wenn man ausreichende Vorsichtsmaßnahmen trifft, muss man keine Vorsichtsmaßnahmen mehr treffen.
        Toller Dampf voraus von Terry Pratchett
        1. Tach!

                  $sql = "SELECT SUM(bestand) AS `summeBestand`, titel 
                            FROM artikel WHERE MATCH(`titel`) AGAINST(? IN BOOLEAN MODE) ";
          
                  $sql = "SELECT SUM(bestand) AS `summeBestand` FROM artikel";
          

          Prüfe mit Kontrollausgaben, ob der Query aussieht, wie er aussehen soll.

          Bei einem Stringliteral, das nicht verändert wird, bringt eine Kontrollausgabe auch keine neuen Erkenntnisse.

          Zudem hast du keine Fehlerbehandlung. Wenn einer deiner Queries wegen eines Fehlers nicht ausgeführt wird, erfährst du ohne Fehlerausgabe nichts relevantes darüber.

          Das ist der entscheidende Punkt. Viele PHP-Funktionen geben im Fehlerfall einen anderen Wert zurück. Den muss man auswerten, wenn man nicht nur für schönes Wetter programmiert.

          dedlfix.

          1. Hallo

                    $sql = "SELECT SUM(bestand) AS `summeBestand`, titel 
                              FROM artikel WHERE MATCH(`titel`) AGAINST(? IN BOOLEAN MODE) ";
                    $res = $mysqli->prepare($sql);
                    $res->bind_param("s", $Eingabe);
            

            Prüfe mit Kontrollausgaben, ob der Query aussieht, wie er aussehen soll.

            Bei einem Stringliteral, das nicht verändert wird, bringt eine Kontrollausgabe auch keine neuen Erkenntnisse.

            Ich benutze das zusammenknippern nicht, kann also über spezielle Eigenheiten nichts sagen. Wenn in $Eingabe aber nicht der erwartete Wert drin steht und daraufhin der Vergleich mit der Spalte titel keine passenden Ergebnisse liefert, sollte man vor der Ausführung schon einmal auf den Query schauen. Das sollte man mMn unabhängig von den zur Übergabe des Queries benutzten Methode tun.

            Tschö, Auge

            --
            Wenn man ausreichende Vorsichtsmaßnahmen trifft, muss man keine Vorsichtsmaßnahmen mehr treffen.
            Toller Dampf voraus von Terry Pratchett
            1. Tach!

              Ich benutze das zusammenknippern nicht, kann also über spezielle Eigenheiten nichts sagen. Wenn in $Eingabe aber nicht der erwartete Wert drin steht und daraufhin der Vergleich mit der Spalte titel keine passenden Ergebnisse liefert, sollte man vor der Ausführung schon einmal auf den Query schauen. Das sollte man mMn unabhängig von den zur Übergabe des Queries benutzten Methode tun.

              Anschauen reicht in dem Fall, eine Kontrollausgabe ergibt hier keinen Sinn. Man könnte aber die Query kopieren und die Prepared-Statement-Platzhalter durch feste Werte ersetzen und die Query in einer Testumgebung laufen lassen, beispielsweise in phpMyAdmin.

              dedlfix.

              1. Hallo

                Ich benutze das zusammenknippern nicht, kann also über spezielle Eigenheiten nichts sagen. Wenn in $Eingabe aber nicht der erwartete Wert drin steht und daraufhin der Vergleich mit der Spalte titel keine passenden Ergebnisse liefert, sollte man vor der Ausführung schon einmal auf den Query schauen. Das sollte man mMn unabhängig von den zur Übergabe des Queries benutzten Methode tun.

                Anschauen reicht in dem Fall, eine Kontrollausgabe ergibt hier keinen Sinn.

                Hmm, für mich ist das – natürlich nur im Entwicklungsprozess – gleichbedeutend. Dem Besucher einer Seite mit dem fertigen Produkt sollte man so etwas natürlich nicht anzeigen.

                Tschö, Auge

                --
                Wenn man ausreichende Vorsichtsmaßnahmen trifft, muss man keine Vorsichtsmaßnahmen mehr treffen.
                Toller Dampf voraus von Terry Pratchett
                1. Tach!

                  Anschauen reicht in dem Fall, eine Kontrollausgabe ergibt hier keinen Sinn.

                  Hmm, für mich ist das – natürlich nur im Entwicklungsprozess – gleichbedeutend. Dem Besucher einer Seite mit dem fertigen Produkt sollte man so etwas natürlich nicht anzeigen.

                  Irgendwie verstehst du mich grad nicht.

                  $x = 'foo';

                  Man braucht keine Kontrollausgabe für ein einfaches Stringliteral. Auch nicht zum Testen. Das was im String steht ist das was im Code steht.

                  Was du vermutlich im Kopf hast ist ein Konstrukt bei dem sprintf() oder Verknüpfungsoperatoren verwendet werden, um einen String zusammenzusetzen. Da ist das natürlich sinnvoll. Aber das liegt hier grad nicht vor. Und man kann auch nicht schauen, wie das zusammengesetzte Prepared Statement aussieht, weil das außerhalb des Einflussbereichs des PHP-Programmierers stattfindet - falls MySQL da überhaupt was zusammensetzt.

                  dedlfix.

                  1. Hallo

                    Anschauen reicht in dem Fall, eine Kontrollausgabe ergibt hier keinen Sinn.

                    Hmm, für mich ist das – natürlich nur im Entwicklungsprozess – gleichbedeutend. Dem Besucher einer Seite mit dem fertigen Produkt sollte man so etwas natürlich nicht anzeigen.

                    $x = 'foo';

                    Man braucht keine Kontrollausgabe für ein einfaches Stringliteral. Auch nicht zum Testen. Das was im String steht ist das was im Code steht.

                    Die Frage, die sich zumindest mir stellt, ist ja, ob da (also in $x) wirklich der gewünschte Wert drin steht. Das ist ja oft genug nicht der Fall. Lass es eine falsche Zuweisung an die Variable oder auch eine falsche Übergabe an den Funktionsparameter sein.

                    Es muss ja nicht einmal ein „richtiger“ Fehler auftreten. Es reicht, wenn ein Wert übergeben wird, bei dem das MATCH aus der WHERE-Klausel nie und nimmer zutreffen wird. Für den Außenstehenden kommt einfach nichts raus (warum auch immer). Woran das liegt, weiß man dann nicht.

                    Und man kann auch nicht schauen, wie das zusammengesetzte Prepared Statement aussieht, weil das außerhalb des Einflussbereichs des PHP-Programmierers stattfindet

                    Da schlägt meine Unkenntnis über die Methode mit den Bindings zu. Wenn der ganze Kram als Einzelteile mit der Anweisung, sie auf der Zielseite zu verknüpfen, übergeben wird, bekommt man im anweisenden PHP-Skript natürlich nie einen „fertigen“ Query zu sehen.

                    Tschö, Auge

                    --
                    Wenn man ausreichende Vorsichtsmaßnahmen trifft, muss man keine Vorsichtsmaßnahmen mehr treffen.
                    Toller Dampf voraus von Terry Pratchett
  2. Hallo und guten Morgen,

    Was mache ich falsch?

    an der Stelle, an der Du $res->bind_param("s", $Eingabe); stehen hast im Programmfluss, ist $res noch gar nicht passend definiert.

    Grüße
    TS

    --
    es wachse der Freifunk
    http://freifunk-oberharz.de
    1. Guten Morgen,

      an der Stelle, an der Du $res->bind_param("s", $Eingabe); stehen hast im Programmfluss, ist $res noch gar nicht passend definiert.

      ist mir auch gerade aufgefallen, siehe ein Posting weiter oben. Allerdings erhalte ich jetzt kein Ergebnis. SUM wird irgendwie nicht angewendet.

      EDIT: Im $res->bind_result hat §titel gefehlt. Jetzt zeigt SUM auch das richtige Ergebnis an. Danke für die Hilfe.

  3. Hallo,

    an alle PHP Speziallisten, ist der Code so OK oder kann man daran noch etwas verbessern?

    function bestandNachEingabe($mysqli, $Eingabe=false){
            
        if ($Eingabe) {
    
            $sql = "SELECT SUM(bestand) AS `summeBestand`
                      FROM artikel WHERE MATCH(`titel`) AGAINST(? IN BOOLEAN MODE) ";
            $res = $mysqli->prepare($sql);
            $res->bind_param("s", $Eingabe);
                
        }
            
        else {
    
            $sql = "SELECT SUM(bestand) AS `summeBestand` FROM artikel";
            $res = $mysqli->prepare($sql);
    
        }
        $res->execute();
        $res->bind_result($summeBestand);
        $res->fetch();
        $res->close();  
    
        return $summeBestand; 
    }
    
    1. Hallo

      an alle PHP Speziallisten, ist der Code so OK oder kann man daran noch etwas verbessern?

      Immer noch keine Fehlerbehandlung. [1]

      Tschö, Auge

      --
      Wenn man ausreichende Vorsichtsmaßnahmen trifft, muss man keine Vorsichtsmaßnahmen mehr treffen.
      Toller Dampf voraus von Terry Pratchett

      1. Ja, mir ist klar, dass es wahrscheinlich ist, dass du mein anderes Posting noch nicht gelesen hattest, als du deines schriebst. ↩︎

      1. Hallo,

        Immer noch keine Fehlerbehandlung. [^1]

        doch, ich hatte dein Posting gelesen allerdings nicht deine editierte Version. Die Fehlerbehandlung baue ich gleich ein.