Ankündigung

Einklappen
Keine Ankündigung bisher.

MySql Abfrage mit bis zu 3 Bedingungen und Between

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

  • #16
    Mal die Fehler ausgeben lassen: https://php-de.github.io/jumpto/sql/...ehler-ausgeben

    Und die Lücke ist immer noch da!

    "geklärt
    Und scheibar hast du ein Encoding Problem. Bei Gelegenheit mal anschauen -> https://php-de.github.io/jumpto/utf-8/
    Debugging: Finde DEINE Fehler selbst! | Gegen Probleme beim E-Mail-Versand | Sicheres Passwort-Hashing | Includes niemals ohne __DIR__
    PHP.de Wissenssammlung | Kein Support per PN

    Kommentar


    • #17
      Code:
      $sql = ""SELECT * FROM aktionen WHERE datum BETWEEN '".$ausdatum."' AND '".$ausdatum1."'";
      doppeltes " gleich zum Anfang, deshalb ist das code highlighting auch so komisch.
      Die SQL Anweisung kommt dabei raus, in etwa so:
      "in etwa so" machen wir hier nicht




      ... ach du sendest die Query wirklich innerhalb von Anführungszeichen an die DB. Mach die mal weg.
      Relax, you're doing fine.
      RTFM | php.de Wissenssammlung | Datenbankindizes | Stay fit

      Kommentar


      • #18
        Hoppala, da ist mir wohl beim wieder zusammen bauen ein \ abhanden gekommen

        PHP-Code:
        $sql ""SELECT FROM aktionen WHERE datum BETWEEN '".$ausdatum."' AND '".$ausdatum1."'"; 
        (ok, merke nach dem Abspeichern das \ entfernt wird, also vor dem zweiten " ist ein \)

        Das zweite sollte eigentlich escaped sein (schreibt man das so? )

        in etwa so, weil je nachdem was ausgewählt wurde eine ähnliche Abfrage dabei raus kommt.

        Ich werde mich da morgen nochmal ran setzen, es muss ja eine Lösung geben, die
        a) funktioniert
        und b) sicher ist

        Hatte schon überlegt die Daten alles aus der DB zu lesen und anschließend zu filtern. So lange die DB noch klein ist, wird das sicher gehen, aber
        irgendwann denke ich mal ist das weniger sinnvoll.

        Ich mach das noch nicht so lange, daher bin ich da wohl noch recht unwissend, sorry...

        Grüße

        Kommentar


        • #19
          moin,

          die Abfrage, die am Ende tatsächlich bei der Datenbank landet, sollte nicht
          Code:
          "SELECT * FROM aktionen WHERE datum BETWEEN '2018-05-02' AND '2018-05-02' AND shop='Rendsburg' AND erledigt='0' AND aktion='termin' ORDER BY id"  
          sondern

          Code:
          SELECT * FROM aktionen WHERE datum BETWEEN '2018-05-02' AND '2018-05-02' AND shop='Rendsburg' AND erledigt='0' AND aktion='termin' ORDER BY id  
          sein. Du verpackst das gerade doppelt als String.

          und b) sicher ist
          Prepared Statements.
          Bau dir die Query so zusammen wie du es aktuelle tust, setz aber Platzhalter statt der tatsächlichen Werte ein. Gleichzeitig gibst du die Werte die da eingesetzt werden müssen in ein Array, dieses Array übergibst du dann an die execute-Methode wenn du das Prepared Statement ausführst.

          ganz grob, so:
          PHP-Code:
          $searchParams = [];

          $sql "SELECT * FROM tabelle WHERE startdate BETWEEN ? AND ?";
          $searchParams[] = $_POST['startFrom'];
          $searchParams[] = $_POST['startTo'];

          if (
          $_POST['test']) !== 'alle') {
             
          $sql .= ' AND testfield = ?';
             
          $searchParams[] = $_POST['test'];
          }

          $statement $pdo->prepare($sql);
          $statement->execute($searchParams); 
          Relax, you're doing fine.
          RTFM | php.de Wissenssammlung | Datenbankindizes | Stay fit

          Kommentar


          • #20
            Moin,

            ich habe das ganze jetzt wie folgt geändert:

            PHP-Code:
            else if ($ausart "Vorgänge Anzeigen") {
              echo 
            '<br>';
              
            $searchparams = [];

              
            $sql "SELECT * FROM aktionen WHERE datum BETWEEN ? AND ?";
              
            $searchparams[] = $ausdatum;
              
            $searchparams[] = $ausdatum1;

              if (
            $ausshop !== 'Alle') {
                
            $sql $sql.' AND shop= ?';
                
            $searchparams[] = $ausshop;
              }

              if (
            $ausstatus === 'offen') {
                
            $sql $sql.' AND erledigt= ?';
                
            $searchparams[] = 0;
              } else if (
            $ausstatus === 'geschlossen') {
                
            $sql $sql.' AND erledigt= ?';
                
            $searchparams[] = 1;
              }

              if (
            $ausart2 === 'Termin') {
                
            $sql $sql.' AND aktion= ?';
                
            $searchparams[] = 'termin';
              } else if (
            $ausart2 === 'in Shop') {
                
            $sql $sql.' AND aktion= ?';
                
            $searchparams[] = 'shop';
              } else if (
            $ausart2 === 'Rückruf') {
                
            $sql $sql.' AND aktion= ?';
                
            $searchparams[] = 'rueckruf';
              } else if (
            $ausart2 === 'geklärt') {
                
            $sql $sql.' AND aktion= ?';
                
            $searchparams[] = 'geklaert';
              }

              
            $sql $sql." ORDER BY id";
              
            $statement $pdo->prepare($sql);
              
            $statement->execute($searchparams);
              
            $i 0;

              while(
            $row $statement->fetch()) {
                
            // nur zum Testen...
                
            $i++;
                echo 
            $i.'<br>';
                echo 
            $row['kdname'].'<br>';
              }

              echo 
            $sql.'<br>';
              echo 
            $ausshop.'<br>';
              echo 
            $ausstatus.'<br>';
              echo 
            $ausart2.'<br>';
              die; 
            Als $sql kommt dann folgendes dabei raus (je nachdem was Ausgewählt wurde):

            PHP-Code:
            SELECT FROM aktionen WHERE datum BETWEEN ? AND ? AND shop= ? AND erledigt= ? AND aktion= ? ORDER BY id 
            Jetzt bekomme ich auch die gewünschten Ergebnisse aus der Datenbank.
            Vielen Dank an euch für die Hilfe.

            Eine Frage hätte ich aber noch dazu:

            Alle Werte übernehme ich ja jetzt in das Array bevor ich das ganze in die DB jage, und überprüfe die Werte vorher ja entsprechend.
            Nur Anfangs und Enddatum (Welche per Input Date komme) übernehme ich direkt in das Array.
            Ich befürchte ich kenne die Antwort, aber das gibt dann Angreifern noch immer die Möglichkeit Unfug zu treiben oder?
            Wie kann ich aber prüfen ob in $ausdatum und $ausdatum1 wirklich ein valides Datum steht.

            In der DB ist datum vom Format DATE ohne Zeit, da ich die Zeit in der Tabelle nicht benötige. Darum liefert die DB auch Ergebnisse wenn Start und Enddatum Identisch sind,
            zumindest hat sie es bis jetzt gemacht.

            Grüße

            Kommentar


            • #21
              Mal ein paar Hinweise zu deinem Code.

              Verwende am besten durchgängig nur eine Sprache für die Variablenbezeichner
              $ausart vs. $searchparams macht sich nicht besonders gut.

              Zitat von Kornkaefer Beitrag anzeigen
              Nur Anfangs und Enddatum (Welche per Input Date komme) übernehme ich direkt in das Array.
              Nein, das machst du nicht.
              Dein Code dazu
              PHP-Code:
              $sql "SELECT * FROM aktionen WHERE datum BETWEEN ? AND ?";
                
              $searchparams[] = $ausdatum;
                
              $searchparams[] = $ausdatum1
              Deine Beschreibung wäre korrekt,wenn du die POST- Variable dort eingefügt hättest.
              Also
              PHP-Code:
              $searchparams[] = $_POST['datumstart'];
                
              $searchparams[] = $_POST['datumende']; 
              Da das Datum vorab auf Validität geprüft werden soll, kommt entweder die Funktion checkdate() in Frage oder die folgende Funktion, die dir das Fomat schon abnimmt.
              PHP-Code:
              function isDateValid($date$format 'Y-m-d')
              {
                  
              $dt DateTime::createFromFormat($format$date);
                  return 
              $dt && $dt->format($format) == $date;

              Die Funktion gibt TRUE oder FALSE zurück.

              Da du wohl im Formular eine Auswahl triffst ob offen oder erledigt als Status in Frage kommt und du das umständlich umsetzt,
              PHP-Code:
               if ($ausstatus === 'offen') {
                  
              $sql $sql.' AND erledigt= ?';
                  
              $searchparams[] = 0;
                } else if (
              $ausstatus === 'geschlossen') {
                  
              $sql $sql.' AND erledigt= ?';
                  
              $searchparams[] = 1;
                } 
              kommt hier mal eine Alternative.

              Du gibst ja die Werte für die Abfrage vor, nämlich 0 oder 1, damit kann kein anderer Wert in die Query gelangen. Der Umweg über die Variablenbindung im prepared statement ist hier also nicht nötig.
              'Folgender Code macht das gleiche
              PHP-Code:
              if ($ausstatus === 'offen') {
                  
              $sql $sql.' AND erledigt=0';
              }else{
                  
              $sql $sql.' AND erledigt=1';

              Auch hier kannst du die superglobale POST direkt verwenden, ein umkopieren ist nicht nötig..

              Wenn du dann als Vorgabe immer alle offenen anzuzeigen vorgeben willst, kannst du das auch umdrehen
              PHP-Code:
              if ($_POST['status'] === 'geschlossen') {
                  
              $sql $sql.' AND erledigt=1';
              }else{
                  
              $sql $sql.' AND erledigt=0';

              Schau dir dazu mal folgende Artikel in der Wissenssammlung an
              https://php-de.github.io/jumpto/waechter/
              und
              https://php-de.github.io/jumpto/auswahllisten/

              Insgesamt scheint mir, dass du das Prinzip von prepared statements noch nicht verstanden hast, auch wenn du weisst wie man es kopiert und Vraiblen ersetzt.

              Validierung vpn Daten sollten man dennoch immer machen, auch wenn man prepared statements, verwendet, denn oftmals will man evtl auf falsche Eingaben reagieren, oder Bots davon abhalten mehr Informationen über den Code zu erlangen.




              Kommentar

              Lädt...
              X