问题描述
**已编辑
@H_502_5@$sql_2 = "SELECT disTINCT cr.id AS courseid,cr.fullname AS coursename,cr.idnumber AS idnumber,COUNT(disTINCT ra.id) AS enrols,COUNT(disTINCT cc.timecompleted) AS completed FROM {course} cr JOIN {context} ct ON ( ct.instanceid = cr.id ) LEFT JOIN {role_assignments} ra ON ( ra.contextid = ct.id ) and ra.roleid = 5 LEFT JOIN {course_completions} cc ON (cc.course = cr.id) WHERE cr.id = :course_id GROUP BY cr.fullname,cr.id"; $sql_3 = "SELECT disTINCT u.id AS userid,u.email AS email,u.lastaccess,c.id AS courseid FROM {user} u JOIN {role_assignments} ra ON ra.userid = u.id LEFT JOIN {context} ct ON ct.id = ra.contextid AND ra.roleid = 5 LEFT JOIN {course} c ON c.id = ct.instanceid AND ct.contextlevel = 50 WHERE c.id = :course_id"; $sql_4 = "SELECT disTINCT u.id AS userid,sc.name AS item,m.name AS module,cm.id AS cmid,cm.idnumber AS itemidnumber,sc.launch AS launch,cmc.completionstate AS completed,cmc.timemodified AS timecompleted FROM {user} u JOIN {role_assignments} ra ON ra.userid = u.id LEFT JOIN {context} ct ON ct.id = ra.contextid AND ra.roleid = 5 LEFT JOIN {course} c ON c.id = ct.instanceid AND ct.contextlevel = 50 LEFT JOIN {course_modules} cm ON cm.course = c.id LEFT JOIN {course_modules_completion} cmc ON cmc.userid = u.id AND cmc.coursemoduleid = cm.id LEFT JOIN {modules} m ON m.id = cm.module LEFT JOIN {scorm} sc ON sc.id = cm.instance WHERE c.id = :course_id and m.id = 18"; $courses = $DB->get_records_sql($sql_2,["course_id" => $requestedcourseids]); $users = $DB->get_records_sql($sql_3,["course_id" => $requestedcourseids]); $modules = $DB->get_records_sql($sql_4,["course_id" => $requestedcourseids]);
我在每个结果下方添加了foreach和for循环,以获取多维数组结果,并获得了像这样的模块结果
@H_502_5@ "course": [ { "courseid": 4,"coursename": "Activities","idnumber": "","enrols": 6,"completed": 1,"users": [ { "userid": 3,"email": "[email protected]","lastaccess": 1599379804,"modules": [ { "userid": 3,"module": "scorm","item": "Vitamin","itemidnumber": "","cmid": 24,"launch": 28,"timecompleted": 1595575023 },{ "userid": 2,"completed": 0,"timecompleted": 1593135761 },{ "userid": 4,"timecompleted": 1589359945 },{ "userid": 8,"completed": null,"timecompleted": null },{ "userid": 7,"timecompleted": null } ] },{ "userid": 2,"email": "[email protected]","lastaccess": 1599635370,"modules": [ { "userid": 9,"timecompleted": 1595576987 },{ "userid": 3,
它应该为每个用户列出8个不同的模块,但是它仅循环6次,这仅是用户数。我想让用户拥有用户尝试过的所有模块。
这是代码
@H_502_5@foreach($courses as $completion) { if(!is_null($course)) { $coursesdata[] = $course; } $course = array(); $course['courseid'] = $completion->courseid; $course['coursename'] = $completion->coursename; $course['idnumber'] = $completion->idnumber; $course['enrols'] = $completion->enrols; $course['completed'] = $completion->completed; $course['users'] = []; if(!empty($users)) { foreach($users as $userinfo) { for($i=0; $i<count($users); $i++) { $user = array(); $user['userid'] = $userinfo->userid; $user['email'] = $userinfo->email; $user['lastaccess'] = $userinfo->lastaccess; $user['modules'] = array(); if(!empty($modules)) { foreach($modules as $details) { for($i=0; $i<count($modules); $i++) { $module = array(); $module['module'] = $details->module; $module['item'] = $details->item; $module['itemidnumber'] = $details->itemidnumber; $module['cmid'] = $details->cmid; $module['launch'] = $details->launch; $module['completed'] = $details->completed; $module['timecompleted'] = $details->timecompleted; } if(!is_null($module)) { $user['modules'][] = $module; } } } } if(!is_null($user)) { $course['users'][] = $user; } } } }
问题:如何将$ modules中的所有数据放在$ users数组下?目前,它仅循环$ modules查询中的第一个元素。
我已经尝试过注释和答案中建议的方法,但这是我到目前为止获得的最接近的方法。
任何帮助或提示都将不胜感激。
谢谢!
解决方法
首先,您当前的代码容易受到sql注入的攻击,您确实应该使用参数https://api.highcharts.com/highcharts/series.polygon。我还将模块分解为另一个查询。
$sql_2 = "SELECT DISTINCT cr.id AS courseid,cr.fullname AS coursename,cr.idnumber AS idnumber,COUNT(DISTINCT ra.id) AS enrols,COUNT(DISTINCT cc.timecompleted) AS completed
FROM {course} cr JOIN {context} ct ON ( ct.instanceid = cr.id )
LEFT JOIN {role_assignments} ra ON ( ra.contextid = ct.id ) and ra.roleid = 5
LEFT JOIN {course_completions} cc ON (cc.course = cr.id)
WHERE cr.id = :course_id GROUP BY cr.fullname,cr.id";
$sql_3 = "SELECT DISTINCT
u.id AS userid,u.email AS email,c.id AS courseid
FROM {user} u
JOIN {role_assignments} ra ON ra.userid = u.id
LEFT JOIN {context} ct ON ct.id = ra.contextid AND ra.roleid = 5
LEFT JOIN {course} c ON c.id = ct.instanceid AND ct.contextlevel = 50
WHERE c.id = :course_id and m.id = 18 ORDER BY u.email";
$sql_4 = "SELECT DISTINCT
u.id AS userid,m.name AS module
FROM {user} u
JOIN {role_assignments} ra ON ra.userid = u.id
LEFT JOIN {context} ct ON ct.id = ra.contextid AND ra.roleid = 5
LEFT JOIN {course} c ON c.id = ct.instanceid AND ct.contextlevel = 50
LEFT JOIN {course_modules} cm ON cm.course = c.id
LEFT JOIN {course_modules_completion} cmc ON cmc.userid = u.id AND cmc.coursemoduleid = cm.id
LEFT JOIN {modules} m ON m.id = cm.module
LEFT JOIN {scorm} sc ON sc.id = cm.instance
WHERE c.id = :course_id and m.id = 18 ORDER BY u.email";
$courses = $DB->get_records_sql($sql_2,["course_id" => $requestedcourseids]);
$users = $DB->get_records_sql($sql_3,["course_id" => $requestedcourseids]);
$modules = $DB->get_records_sql($sql_4,["course_id" => $requestedcourseids]);
$course_user_modules = [];
foreach($courses as $course){
$course["users"] = [];
foreach($users as $course_user){
if($course["courseid"]==$course_user["courseid"]){
unset($course_user["courseid"]);
$course_user["modules"] = [];
foreach($modules as $user_module){
if($user_module["userid"]==$course_user["userid"]){
unset($user_module["userid"]);
array_push($course_user["modules"],$user_module);
}
}
array_push($course["users"],$course_user);
}
}
array_push($course_user_modules,$course);
}
,
我在Moodle数据库调用get_records_sql
$modules = $DB->get_records_sql($sql_4,["course_id" => $requestedcourseids]);
这将返回结果中第一个字段索引的数组。在我的情况下,这意味着每个用户ID仅返回一组数组。 在将sql查询的moduleid(唯一值)更改为第一位之后,它现在已按预期工作。
$sql_4 = "SELECT DISTINCT cm.id AS moduleid,u.id AS userid,sc.name AS item,m.name AS module,cm.idnumber AS itemidnumber,sc.launch AS launch,cmc.completionstate AS completed,cmc.timemodified AS timecompleted
FROM {user} u
JOIN {role_assignments} ra ON ra.userid = u.id
LEFT JOIN {context} ct ON ct.id = ra.contextid AND ra.roleid = 5
LEFT JOIN {course} c ON c.id = ct.instanceid AND ct.contextlevel = 50
LEFT JOIN {course_modules} cm ON cm.course = c.id
LEFT JOIN {course_modules_completion} cmc ON cmc.userid = u.id AND cmc.coursemoduleid = cm.id
LEFT JOIN {modules} m ON m.id = cm.module
LEFT JOIN {scorm} sc ON sc.id = cm.instance
WHERE c.id = :course_id and m.id = 18 and u.id = :userid";
在出现之前,
users:
userid: 2,module:
moduleid: 12,userid: 8,module:
moduleid: 12
userid: 9,
现在我明白了,
users:
userid: 2,moduleid: 14,moduleid: 17,userid: 9,
这篇文章帮助我进行了梳理。 get_records_sql returns only one result using inner join in moodle