phpwhile-loopsubmit-button

isset function submits all buttons inside the while loop PHP


im having this problem where the submit button inside the while loop re-execute the while loop.

PHP:

$query1 = $con->query("SELECT * FROM room");
if($query1->num_rows > 0) {
    while($row1 = $query1->fetch_array()) {
        $idroom = $row1['idroom'];

        echo "<tr>";
        echo "<td> $idroom </td>";
        echo "<td> <form method='POST'> <input type='submit' name='delete' value='DELETE'> </form></td>";
        echo "</tr>";

        if(isset($_POST['delete'])) {
            $query2 = $con->query("DELETE FROM room WHERE idroom='$idroom'");
        }
    }
}

the table: [1]: https://i.sstatic.net/dujps.png

the problem is, when i click the delete button, it just deletes all of the room INSTEAD OF the room that i want to delete. i believe the program thinks that i presses all of the delete button at once because of the 'isset' function.

things that ive tried:


Solution

  • There are lots of things wrong with this code, not least that it is incredibly insecure and vulnerable to injection. You should read about prepared statements before you go any further. There are no end of tutorials and SO answers for this so I won't cover them here. In the interests of helping out a new programmer (I was new not that long ago) I will point out what I believe is going wrong here:

    1. $query1 = $con->query("SELECT * FROM room");

    This is run every time the script runs. This is a key thing to realise. If you load the page, or if you submit a post delete this always happens. Which leads to:

    1. if($query1->num_rows > 0) { while($row1 = $query1->fetch_array()) { ...

    You start your loop, looping through every record. Notice the every.

    So for every single record, you then check:

    1. if(isset($_POST['delete'])) {...

    This is where your records are removed and what CBroe was pointing towards in his comment. You believe (I think) that you check for the deletion of this individual record however you only check isset($_POST['delete']) and you do this for EVERY record. Remember, the POST variable exists until the end of the script or until removed. So by clicking delete, and submitting that _POST value you pass this condition for every record in your loop.

    So the solution. Well I'm not going to write it for you, there are different options. You should be passing some kind of identifier to the the post that is specific to the record you want, and then you need to check that e.g. isset POST[delete] && isset(POST['room_id']). Then you need to decide the best place to be doing it, at the start of the script, in a different script, probably not inside a loop (that's rarely a sign of great programming). If you are going to remove a record you should probably be doing it before you create output for it. (why collect a record just to then delete it, is that efficient?).

    If you really must do it inside a loop then you need some kind of check that the id of the room is the same as the id of the post value before you run the delete.

    Hopefully that is helpful, but ensure you look into and start using prepared statements as a matter of urgency - there's really no excuse not to do so in 2020