Ankündigung

Einklappen
Keine Ankündigung bisher.

[Erledigt] call_user_func_array und bind_param Problem

Einklappen

Neue Werbung 2019

Einklappen
X
  • Filter
  • Zeit
  • Anzeigen
Alles löschen
neue Beiträge

  • [Erledigt] call_user_func_array und bind_param Problem

    Hey
    Ich möchte sämtliche MySQLi-Anweisungen in eine einzige Klasse packen. Das klappt soweit ganz gut, bei den Prepared-Statements allerdings stoße ich auf ein Problem. Folgende Methode soll die Anweisung bind_param() übernehmen. Dafür generiere ich ein Array mit allen übergebenen Parametern, welche ich dann an die bind_param() weiterleite, so dass man dann später bequem mit $objekt->set_parameter($bind, $value) die "Variablen" befüllen kann.
    Der Code dazu sieht so aus:
    PHP-Code:
    function bind()
        {
            
    //Minimum 2 Argumente werden benötigt
            
    $arg_num func_num_args();
            if (
    $arg_num 1) return false;
            
            
    $datastring func_get_arg(0);
            
    $i 1//0 wird übersprungen da im $datastring
            
    while ($i $arg_num)
            {
                
    $this->params[func_get_arg($i)] = "test"//Das Array mit den "gebindeten" Variablen
                
    $i++;
            }
            
            
    //$datastring an das array anfügen, zwecks funktionsaufruf
            
    array_unshift($this->params, &$datastring);
            
    //bind_param aufrufen und Parameter übergeben 
                    
    if (!call_user_func_array(array($this->prep_obj"bind_param"), &$this->params))
                
    $this->exc("Parameter konnten nicht gebunden werden!");
                    } 
    Die Variablen werden dann so befüllt:
    PHP-Code:
    function set_parameter($parameter$value)
        {
            
    $this->params[$parameter] = &$value;
            
        } 
    Das Array wird auf diese Art richtig angepasst (das ergab ein die() ), wenn ich dann allerdings ein execute() aufrufe wird bei einem INSERT-Kommando nicht das eingetragen was ich über set_parameter() festgelegt habe, sondern das was beim initialisieren des arrays eingetragen wurde in die datenbank geschrieben (in dem fall hier also immer "test").

    Beim Nachforschen bin ich auf einen Hinweis auf php.net gestoßen:
    Hinweis: Care must be taken when using mysqli_stmt_bind_param() in conjunction with call_user_func_array(). Note that mysqli_stmt_bind_param() requires parameters to be passed by reference, whereas call_user_func_array() can accept as a parameter a list of variables that can represent references or values.
    Aber das hilft mir nicht weiter, meiner Meinung nach werden alle Werte korrekt by reference übergeben?!

    Danke für Hilfe

  • #2
    Versteh nicht, was das für einen SInn haben soll?
    [COLOR="#F5F5FF"]--[/COLOR]
    [COLOR="Gray"][SIZE="6"][FONT="Georgia"][B]^^ O.O[/B][/FONT] [/SIZE]
    „Emoticons machen einen Beitrag etwas freundlicher. Deine wirken zwar fachlich richtig sein, aber meist ziemlich uninteressant.
    [URL="http://www.php.de/javascript-ajax-und-mehr/107400-draggable-sorttable-setattribute.html#post788799"][B]Wenn man nur Text sieht, haben viele junge Entwickler keine interesse, diese stumpfen Texte zu lesen.“[/B][/URL][/COLOR]
    [COLOR="#F5F5FF"]
    --[/COLOR]

    Kommentar


    • #3
      Das ich alles was mit Datenbanken zu tun hat in einer Klasse habe. Fehlerüberprüfungen etc. kann ich mir damit schon vereinfachen.
      Wie würdest du es denn machen?

      Und selbst wenn das Unsinn sein sollte - warum funktioniert es nicht?

      Kommentar


      • #4
        mysqli ist bereits eine Klasse mit allen Funktionen in einem Objekt.

        Ich verstehe schon allein Deinen Plan mit set_parameter nicht, weil da ja das Type-Binding fehlt.
        [COLOR="#F5F5FF"]--[/COLOR]
        [COLOR="Gray"][SIZE="6"][FONT="Georgia"][B]^^ O.O[/B][/FONT] [/SIZE]
        „Emoticons machen einen Beitrag etwas freundlicher. Deine wirken zwar fachlich richtig sein, aber meist ziemlich uninteressant.
        [URL="http://www.php.de/javascript-ajax-und-mehr/107400-draggable-sorttable-setattribute.html#post788799"][B]Wenn man nur Text sieht, haben viele junge Entwickler keine interesse, diese stumpfen Texte zu lesen.“[/B][/URL][/COLOR]
        [COLOR="#F5F5FF"]
        --[/COLOR]

        Kommentar


        • #5
          Hmm es wäre vielleicht einfacher gewesen einfach von der Klasse zu erben und zu erweitern oder was meinst du?

          Und zu set_parameter:
          mysqli->bind_param($typ, $variable1, $variable2,...) erwartet als ersten parameter ja den typ für die variablen die ihm danach übergeben werden. Also ist mir im Moment ja nicht bekannt welcher Type erwartet wird oder?! Und das ganze muss überhaupt erst so kompliziert werden weil ich ja nicht weiß wieviele Parameter an das bind_param übergeben werden müssen, deswegen der Umweg über ein Array das alle "Variablen" enthält die an die methode übergeben werden sollen, und die Werte dieses Arrays ändert man über set_parameter().

          Kommentar


          • #6
            Aus genau diesem Grund ist es zwecklos, einen Wrapper zu schreiben.
            Also ist mir im Moment ja nicht bekannt welcher Type erwartet wird oder?!
            Wem, wenn nicht Dir! Gerade die Typvorgabe ist wichtig, da ja dadurch die Sicherheit erreicht wird. Wenn Du die Parameter einzeln binden willst, kannst DU das ja machen, die Typvorgabe musst Du trotzdem angeben, sonst ist Dein gesamtes Konzept nichts wert.
            Allerdings frage ich mich auch ernsthaft, welchen Wert ein Objekt mit dynamischen Parametern hat, wenn Du sowieso irgendwo die zugrundeliegende Query statisch angeben musst.
            [COLOR="#F5F5FF"]--[/COLOR]
            [COLOR="Gray"][SIZE="6"][FONT="Georgia"][B]^^ O.O[/B][/FONT] [/SIZE]
            „Emoticons machen einen Beitrag etwas freundlicher. Deine wirken zwar fachlich richtig sein, aber meist ziemlich uninteressant.
            [URL="http://www.php.de/javascript-ajax-und-mehr/107400-draggable-sorttable-setattribute.html#post788799"][B]Wenn man nur Text sieht, haben viele junge Entwickler keine interesse, diese stumpfen Texte zu lesen.“[/B][/URL][/COLOR]
            [COLOR="#F5F5FF"]
            --[/COLOR]

            Kommentar


            • #7
              naja Ziel des Ganzen sollte es eigentlich nur sein den ganzen Datenbankteil auslagern zu können.
              Für einen Profi mag das vielleicht sinnlos erscheinen, mir in ein, zwei monaten hoffentlich auch, aber im moment hab ich vorallemdingen nen relativ großen lerneffekt dadurch!

              Deswegen, egal ob das sinnvoll sein sollt eoder nicht, aber ich würds schon gern zum Laufen bringen.

              Kommentar


              • #8
                Dann beschreibe die Anforderung. Mir ist immer noch nicht klar, wie der Aufruf mit Deinem neuen Objekt aussehen soll.
                [COLOR="#F5F5FF"]--[/COLOR]
                [COLOR="Gray"][SIZE="6"][FONT="Georgia"][B]^^ O.O[/B][/FONT] [/SIZE]
                „Emoticons machen einen Beitrag etwas freundlicher. Deine wirken zwar fachlich richtig sein, aber meist ziemlich uninteressant.
                [URL="http://www.php.de/javascript-ajax-und-mehr/107400-draggable-sorttable-setattribute.html#post788799"][B]Wenn man nur Text sieht, haben viele junge Entwickler keine interesse, diese stumpfen Texte zu lesen.“[/B][/URL][/COLOR]
                [COLOR="#F5F5FF"]
                --[/COLOR]

                Kommentar


                • #9
                  PHP-Code:
                  $db = new db;
                  $db->prepare_query("INSERT INTO user (Feld1, Feld2, Feld3, Feld4) VALUES (?, ?, ?, ?)");
                  $db->bind("ssss""var1""var2""var3""var4");
                  $db->set_parameter("var1""Testnickname");
                  $db->set_parameter("var2""hat keins");
                  $db->set_parameter("var3""100");
                  $db->set_parameter("var4""ÄttDot");
                  $db->execute();
                  $ergebnis $db->fetch_result() 
                  So funktioniert der Aufruf meines neuen Objekts.
                  In der Funktion bind() werden alle übergebenen Variablen in ein assoziatives Array geschrieben (als Offsets) und ihnen wird probehalber der Wert "test" zugewiesen. Über set_parameter kann man dann die einzelnen Werte des Arrays ändern, man gibt den Namen und den Wert an. Das funktioniert soweit auch, wenn ich mir danach das Array ausgebe sind die vorher initialisierten Felder geändert. Wenn ich dann aber execute() aufrufe werden diese Änderungen ignoriert und nur der Wert "test" wird in die Datenbank geschrieben - also nur der Wert der bei der Initialisierung zugewiesen wurde. Da liegt mein Problem.

                  Kommentar


                  • #10
                    Zitat von Ballamann Beitrag anzeigen
                    So funktioniert der Aufruf meines neuen Objekts.
                    Das Erzeugen des neuen DB-Objektes, Vorbereiten der Query, Binden der Variablen und Ausführen - all das läuft ganz genau so, wenn du wirklich das native MySQLi nimmst.

                    Im Grunde hast du nur die Funktionen „umbenannt“ - ausführen musst du sie nach wie vor alle (und bei deinem Code noch ein paar zusätzliche).

                    Gewinn, und damit Sinn des ganzen Unterfangens - absolut keiner.
                    Ausser du betrachtest es als Gewinn, dass dein Code nicht funktioniert. Nicht lauffähige Scripte kann man sich aber auch mit weniger Aufwand basteln.
                    [SIZE="1"]RGB is totally confusing - I mean, at least #C0FFEE should be brown, right?[/SIZE]

                    Kommentar


                    • #11
                      Zitat von ChrisB Beitrag anzeigen
                      Gewinn, und damit Sinn des ganzen Unterfangens - absolut keiner.
                      Neben einer Menge praktischer Erfahrung sind in meinen Funktionen auch Überprüfung auf Fehler, deren Weiterleitung und die Möglichkeit für mehr vorhanden.
                      Warum ich sowas schreibe kann dir doch letztenendes egal sein oder? Ich fange in 3 Monaten eine Ausbildung zum FIAE an und jeden Fehler den ich jetzt mache kann ich mir dann sparen.
                      Ausser du betrachtest es als Gewinn, dass dein Code nicht funktioniert. Nicht lauffähige Scripte kann man sich aber auch mit weniger Aufwand basteln.
                      Wahnsinnig schlauer Spruch. Bist du mit der eigentlichen Frage überfordert oder warum kommt nichts in die Richtung? Ich bin mir sicher das zumindest der Teil der im Moment nicht funktioniert für andere (eigene) Systeme durchaus zu gebrauchen wäre, es wäre also durchaus interessant zu erfahren wo der Fehler liegt.

                      Kommentar


                      • #12
                        bind_param() macht nur Sinn, wenn du Daten an DB übergeben willst, die durch Besuchereingaben (Z.Bsp. per POST aus Formular) reinkommen.

                        PHP-Code:
                        $db = new db;

                        db->prepare_query("INSERT INTO user (Feld1, Feld2, Feld3, Feld4) VALUES (?, ?, ?, ?)");
                        //Parameter einbinden
                        $db->bind_param("ssss"$_POST['var1'], $_POST['var2'], $_POST['var3'], $_POST['var4']);
                        //Ausführen
                        $db->execute();

                        $ergebnis $db->fetch() ; 

                        Kommentar


                        • #13
                          Zitat von makko Beitrag anzeigen
                          bind_param() macht nur Sinn, wenn du Daten an DB übergeben willst, die durch Besuchereingaben (Z.Bsp. per POST aus Formular) reinkommen.

                          Nein, bind_param() macht bei jeder Abfrage Sinn die ich öfter als ein mal ausführen muss.

                          Jetzt mal im Ernst Leute, über den Sinn der ganzen Klasse lässt sich nach Meinung von Nikosch streiten - das seh ich ein. Trotzdem wäre es nett wenn ihr euch der eigentlichen Frage widmen würdet.

                          Total sinnlos ist die Klasse jedenfalls nicht - auch wenn sie wohl nicht gut genug für größere Projekte ist, aber dafür ist man eben Anfänger.

                          Kommentar


                          • #14
                            Zitat von Ballamann Beitrag anzeigen
                            Wahnsinnig schlauer Spruch. Bist du mit der eigentlichen Frage überfordert oder warum kommt nichts in die Richtung?
                            Ziemlich dreist für jemanden, der Hilfe sucht...

                            Des weiteren ist der Aufruf an der Stelle falsch.
                            PHP-Code:
                            function set_parameter($parameter, &$value) {
                                
                            $this->params[$parameter] = $value;

                            Das & muss in den Funktionskopf, wo der Parameter übergeben wird!

                            Nachtrag:
                            Außerdem finde ich diese Klasse auch recht unnötig... Ich würde dir eher empfehlen dir eine DB-Klasse zu schreiben, mit der du einfacher SQL-Queries ausführen kannst... Würde denke ich mehr Sinn machen. Und wenn du dafür keine Lust hast, such dir eine im Netz oder benutz PEAR
                            "My software never has bugs, it just develops random features."
                            "Real programmers don't comment. If it was hard to write, it should be hard to understand!"

                            Kommentar


                            • #15
                              Du solltest Dich mal näher mit PHP PDO auseinandersetzen:

                              Einführung PHP PDO

                              speziell prepared statement

                              PHP-Code:
                                  /*** prepare the SQL statement ***/
                                  
                              $stmt $dbh->prepare("SELECT * FROM animals WHERE animal_id = :animal_id AND animal_name = :animal_name");

                                  
                              /*** bind the paramaters ***/
                                  
                              $stmt->bindParam(':animal_id'$animal_idPDO::PARAM_INT);
                                  
                              $stmt->bindParam(':animal_name'$animal_namePDO::PARAM_STR5);

                                  
                              /*** execute the prepared statement ***/
                                  
                              $stmt->execute(); 
                              Gruß Werner
                              Mein kleines Projekt: Fussball Satrup
                              Wird ein OpenSource CMS für Fussballvereine

                              Kommentar

                              Lädt...
                              X