提问者:小点点

使用PHP处理多对多数据库关系并选择/插入多个复选框值


我的数据库中有以下表格:tbl_学生和tbl_课程
我想到了一个音乐学校的项目,学生可以报名参加一门或多门课程,例如,当我注册一个学生时,可以选择多门课程,比如吉他和钢琴,取决于他的选择(现在我自己注册学生,所以这只是假设)<我发现我必须处理多对多的关系,因为一个学生可以有许多课程,而且在一门课程中有许多学生在其中注册
我所做的下一步是创建一个中间表,我称之为tbl_students_courses,其中包含两个表的主键<我的桌子是这样的:

tbl\U学生

+---------+---------+---------------+---------+
|  st_id  | st_name |    st_email   | st_code |
+---------+---------+---------------+---------+
|    1    |John Doe | doe@gmail.com |  55555  |
+---------+---------+---------------+---------+

tbl_课程

+---------+-----------+--------------------------+
|  cr_id  |  cr_name  |         cr_desc          |
+---------+-----------+--------------------------+
|    1    |   Guitar  | Guitar course description|
+---------+-----------+--------------------------+
|    2    |   Bass    | Bass course description  |
+---------+-----------+--------------------------+
|    3    |   Violin  | Violin course description|
+---------+-----------+--------------------------+
|    4    |   Drums   | Drums course description |
+---------+-----------+--------------------------+
|    5    |   Piano   | Piano course description |
+---------+-----------+--------------------------+

tbl_学生课程

+---------+---------+---------+
|  st_id  |  cr_id  |date_insc|
+---------+---------+---------+
|  -----  |  -----  |  -----  |
+---------+---------+---------+

现在我的问题是,我不知道如何将这些表与我的php代码关联起来。我假设,如果我在注册学生时选择了2门课程,那么应该在中间表上创建2条记录,其中只有cr_id彼此不同
另一个问题是使用php通过复选框获取课程ID,因此当我选择例如钢琴和吉他复选框时,它应该返回两门课程的ID,运行查询并插入记录<注意:在我的php代码中,foreach循环显然只是拾取字符串,而不是我想要的课程ID

这是我的HTML:

<div class="form-group">
                   <label class="col-form-label">Select the courses</label>
                   <div class="form-check">
                       <div class="form-check form-check-inline">
                           <input class="form-check-input" name="course[]" type="checkbox" value="Guitar">
                           <label class="form-check-label" >Guitar</label>
                       </div>
                       <div class="form-check form-check-inline">
                           <input class="form-check-input" name="course[]" type="checkbox" value="Bass">
                           <label class="form-check-label" >Bass</label>
                       </div>
                       <div class="form-check form-check-inline">
                           <input class="form-check-input" name="course[]" type="checkbox" value="Violin">
                           <label class="form-check-label" >Violin</label>
                       </div>
                       <div class="form-check form-check-inline">
                           <input class="form-check-input" name="course[]" type="checkbox" value="Drums">
                           <label class="form-check-label" >Drums</label>
                       </div>
                       <div class="form-check form-check-inline">
                           <input class="form-check-input" name="course[]" type="checkbox" value="Piano">
                           <label class="form-check-label" >Piano</label>
                       </div>
                   </div>

以下是我的PHP:

 <?php

            if (isset($_POST['submit'])) {
                include_once '../includes/functions.php';
                $studentName     = addslashes($_POST['sname']);
                $studentEmail    = addslashes($_POST['semail']);
                $studentCode     = intval($_POST['scode']);   
                $studentcourse    = $_POST['course'];   
                $query  = "INSERT INTO tbl_students (st_name, st_id, st_code) "
                . "VALUES ('$studentName', '$studentEmail', '$studentCode')";
                $link   = connection_db(); 
                $result = mysqli_query($link, $query);
        
                if($result){
                    $sql = "SELECT LAST_INSERT_ID()";
                    $result = mysqli_query($link, $sql);
                    $last = mysqli_fetch_assoc($result);

                    foreach($studentcourse as $value){
                        $data = date('Y-m-d H:i:s');
                        $lastID =($last["LAST_INSERT_ID()"]);
                        $sql = "INSERT INTO tbl_students_courses (st_id, cr_id, date_insc) VALUES ($lastID, '$value', '$data')";
                        $result = mysqli_query($link, $sql);
                    }
                    echo "<script>alert('Data saved successfully');</script>";
                    print "<script>top.location = 'index.php?id=2';</script>";
                } else {
                    echo "<script>alert('ERROR! Could not save data');</script>";
                }   
            }
        ?>

我们非常感谢您对改进问题的任何帮助或建议。


共1个答案

匿名用户

如果您将ID作为值放入复选框中,那么代码实际上可以工作

所以我宁愿使用

 <input class="form-check-input" name="course[]" type="checkbox" value="Piano">

改打这个

 <input class="form-check-input" name="course[]" type="checkbox" value="5">

ofc手动输入ID并不是很好,所以您必须从数据库中读取所有课程,并根据数据生成复选框。

所以你可以创建函数从数据库中获取所有课程,就像这样

function getAllCourses(mysqli $link){
    $sql ="SELECT cr_id,cr_name,cr_desc FROM tbl_courses";
    $result = mysqli_query($link, $sql);
    $courses = [];
    while($row = mysqli_fetch_assoc($result)){
        $courses[]=$row;
    }
    return $courses;
}

然后在你生成超文本标记语言代码之前的地方,你可以得到所有的代码

$courses = getAllCourses($link);

之后,您可以像这样生成HTML代码

<div class="form-group">
    <label class="col-form-label">Select the courses</label>
    <div class="form-check">
        <?php
        foreach ($courses as $course): ?>
            <div class="form-check form-check-inline">
                <input class="form-check-input" name="course[]" type="checkbox" value="<?= $course['cr_id'] ?>">
                <label class="form-check-label"><?= $course['cr_name'] ?></label>
            </div>
        <?php
        endforeach; ?>
    </div>

这样,您就不需要获取最后一个插入ID,因为您已经有了studends。

我还看到,您的SQL代码是不安全的,您只需将POST值放入SQL查询中,这样就可以进行SQL注入,您需要在这里使用Prepare语句。其中,您准备了一个带有占位符的SQL语句,并使用值执行它们。

$query  = "INSERT INTO tbl_students (st_name, st_email st_code) "
                . "VALUES (?,?,?)";
$statement = mysqli_repapre($link, $query);
mysqli_stmt_bind_param($statement,"sis",$studentName,$studentEmail,$studentCode);
mysqli_stmt_execute($statement); 

这段代码没有经过测试,但我希望它能给你一个想法。