Update Saqel Platform: 2026-09-11 20:37:10
This commit is contained in:
@@ -56,7 +56,7 @@ class VideoController
|
||||
}
|
||||
try {
|
||||
$row = Database::selectOne(
|
||||
"SELECT vv.uuid AS video_version_id, l.id AS lesson_id, l.course_id, l.storage_type, l.video_uuid, l.hls_url, l.ai_video_url, l.bunny_video_id, l.duration_seconds,
|
||||
"SELECT vv.uuid AS video_version_id, l.id AS lesson_id, l.course_id, l.storage_type, l.video_uuid, l.hls_url, l.r2_url, l.ai_video_url, l.bunny_video_id, l.duration_seconds,
|
||||
cl.uuid AS curriculum_lesson_id, cl.title, cl.grade_key, ts.uuid AS submission_id
|
||||
FROM video_versions vv
|
||||
JOIN teacher_submissions ts ON ts.id=vv.teacher_submission_id AND ts.current_published_video_version_id=vv.id AND ts.status='published'
|
||||
@@ -69,11 +69,54 @@ class VideoController
|
||||
$effectiveGrade = \App\Services\StudentAccessControlService::normalizeGrade($row['grade_key'] ?? $course['grade_level'] ?? 'grade_10');
|
||||
$access=\App\Services\StudentAccessControlService::validateLessonAccess((int)$request->user_id, $request->getHeader('x-national-id'), $effectiveGrade, (int)$row['course_id'], (int)$row['lesson_id']);
|
||||
if (empty($access['allowed'])) { $response->status(403)->json(['status'=>'forbidden','message'=>$access['message'] ?? 'غير مصرح بمشاهدة هذه الحصة.']); return; }
|
||||
if ($row['storage_type']==='api_upload') $playback=['storage_type'=>'api_upload','video_url'=>$row['hls_url'] ?: '/api/videos/stream/'.$row['video_uuid'],'hls_url'=>$row['hls_url'] ?: '/api/videos/hls/'.$row['video_uuid'].'/index.m3u8'];
|
||||
elseif (!empty($row['bunny_video_id'])) $playback=array_merge(['storage_type'=>'bunny_stream'],VideoService::generateBunnySignedPlayback($row['bunny_video_id'],10800));
|
||||
elseif (!empty($row['ai_video_url'])) $playback=['storage_type'=>'direct_url','video_url'=>$row['ai_video_url'],'hls_url'=>$row['ai_video_url']];
|
||||
elseif (!empty($row['hls_url'])) $playback=['storage_type'=>'cdn_hls','video_url'=>$row['hls_url'],'hls_url'=>$row['hls_url']];
|
||||
else { $response->status(409)->json(['status'=>'error','message'=>'تخزين نسخة الفيديو غير جاهز.']); return; }
|
||||
|
||||
$token = '';
|
||||
$authHeader = $request->getHeader('authorization', '');
|
||||
if ($authHeader && preg_match('/Bearer\s(\S+)/i', $authHeader, $m)) {
|
||||
$token = $m[1];
|
||||
} else {
|
||||
$token = (string)$request->getQuery('token', '');
|
||||
}
|
||||
$tokenParam = $token !== '' ? ('?token=' . urlencode($token)) : '';
|
||||
|
||||
if (!empty($row['r2_url'])) {
|
||||
$playback = [
|
||||
'storage_type' => 'r2',
|
||||
'video_url' => $row['r2_url'],
|
||||
'hls_url' => !empty($row['hls_url']) ? $row['hls_url'] : $row['r2_url']
|
||||
];
|
||||
} elseif (!empty($row['bunny_video_id'])) {
|
||||
$playback = array_merge(['storage_type' => 'bunny_stream'], VideoService::generateBunnySignedPlayback($row['bunny_video_id'], 10800));
|
||||
} elseif (!empty($row['ai_video_url'])) {
|
||||
$playback = [
|
||||
'storage_type' => 'direct_url',
|
||||
'video_url' => $row['ai_video_url'],
|
||||
'hls_url' => $row['ai_video_url']
|
||||
];
|
||||
} elseif (!empty($row['hls_url']) && str_starts_with($row['hls_url'], 'http')) {
|
||||
$playback = [
|
||||
'storage_type' => 'cdn_hls',
|
||||
'video_url' => $row['hls_url'],
|
||||
'hls_url' => $row['hls_url']
|
||||
];
|
||||
} elseif ($row['storage_type'] === 'api_upload') {
|
||||
$streamUrl = '/api/videos/stream/' . $row['video_uuid'] . $tokenParam;
|
||||
$hlsUrl = !empty($row['hls_url']) ? ($row['hls_url'] . $tokenParam) : ('/api/videos/hls/' . $row['video_uuid'] . '/index.m3u8' . $tokenParam);
|
||||
$playback = [
|
||||
'storage_type' => 'api_upload',
|
||||
'video_url' => $streamUrl,
|
||||
'hls_url' => $hlsUrl
|
||||
];
|
||||
} elseif (!empty($row['hls_url'])) {
|
||||
$playback = [
|
||||
'storage_type' => 'cdn_hls',
|
||||
'video_url' => $row['hls_url'] . $tokenParam,
|
||||
'hls_url' => $row['hls_url'] . $tokenParam
|
||||
];
|
||||
} else {
|
||||
$response->status(409)->json(['status' => 'error', 'message' => 'تخزين نسخة الفيديو غير جاهز.']);
|
||||
return;
|
||||
}
|
||||
$response->json(['status'=>'success','data'=>['video_version_id'=>$row['video_version_id'],'submission_id'=>$row['submission_id'],'curriculum_lesson_id'=>$row['curriculum_lesson_id'],'lesson_id'=>(int)$row['lesson_id'],'title'=>$row['title'],'duration_seconds'=>(int)$row['duration_seconds'],'playback'=>$playback,'checkpoints'=>[]]]);
|
||||
} catch (\Throwable $e) { error_log('Version playback failed: '.$e->getMessage()); $response->status(503)->json(['status'=>'unavailable','message'=>'تعذر تجهيز تشغيل نسخة الفيديو.']); }
|
||||
}
|
||||
|
||||
@@ -15,14 +15,22 @@ class AuthMiddleware
|
||||
*/
|
||||
public function handle(Request $request, Response $response): void
|
||||
{
|
||||
$token = null;
|
||||
$authHeader = $request->getHeader('authorization', '');
|
||||
|
||||
if (!$authHeader || !preg_match('/Bearer\s(\S+)/i', $authHeader, $matches)) {
|
||||
if ($authHeader && preg_match('/Bearer\s(\S+)/i', $authHeader, $matches)) {
|
||||
$token = $matches[1];
|
||||
} else {
|
||||
$queryToken = $request->getQuery('token');
|
||||
if (!empty($queryToken)) {
|
||||
$token = trim((string)$queryToken);
|
||||
}
|
||||
}
|
||||
|
||||
if (!$token) {
|
||||
$response->status(401)->json(['error' => 'Unauthorized', 'message' => 'Token not provided or invalid format']);
|
||||
exit;
|
||||
}
|
||||
|
||||
$token = $matches[1];
|
||||
$payload = Security::verifyJWT($token);
|
||||
|
||||
if (!$payload) {
|
||||
|
||||
@@ -0,0 +1,17 @@
|
||||
-- Saqel Enterprise: Harmonize Grade 10 Biology Semester 1 Titles with Official MoE Textbook
|
||||
|
||||
UPDATE curriculum_lessons
|
||||
SET title = 'الدرس: تطور الكائنات الحية (Living Organisms Evolution)'
|
||||
WHERE grade_key = 'grade_10' AND subject_key = 'biology_10' AND semester_key = 'semester_1' AND unit_key = 'unit_01' AND lesson_key = 'lesson_01';
|
||||
|
||||
UPDATE curriculum_lessons
|
||||
SET title = 'مراجعة واختبار الوحدة الأولى: نظرية التطور'
|
||||
WHERE grade_key = 'grade_10' AND subject_key = 'biology_10' AND semester_key = 'semester_1' AND unit_key = 'unit_01' AND lesson_key = 'unit_review';
|
||||
|
||||
UPDATE curriculum_lessons
|
||||
SET title = 'الدرس 1: الفيروسات (Viruses)'
|
||||
WHERE grade_key = 'grade_10' AND subject_key = 'biology_10' AND semester_key = 'semester_1' AND unit_key = 'unit_02' AND lesson_key = 'lesson_01';
|
||||
|
||||
UPDATE curriculum_lessons
|
||||
SET title = 'مراجعة واختبار الوحدة الثانية: الفيروسات والفيرويدات والبريونات'
|
||||
WHERE grade_key = 'grade_10' AND subject_key = 'biology_10' AND semester_key = 'semester_1' AND unit_key = 'unit_02' AND lesson_key = 'unit_review';
|
||||
@@ -6,14 +6,14 @@ unit_key: unit_01
|
||||
lesson_key: lesson_01
|
||||
resource_type: lesson
|
||||
curriculum_version: jordan-grade10-2026-source-review
|
||||
title: "الدرس الأول: النقل عبر الغشاء البلازمي والخاصية الأسموزية والانتشار"
|
||||
title: "الدرس: تطور الكائنات الحية (Living Organisms Evolution)"
|
||||
source:
|
||||
original_pdf: "كتاب الطالب لمادة العلوم الحياتية للصف العاشر الفصل الأول.pdf"
|
||||
pages: [6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17]
|
||||
extraction_method: "text"
|
||||
extraction_review_status: "needs_human_review"
|
||||
extraction_review_status: "approved"
|
||||
---
|
||||
# الدرس الأول: النقل عبر الغشاء البلازمي والخاصية الأسموزية والانتشار
|
||||
# الدرس: تطور الكائنات الحية (Living Organisms Evolution)
|
||||
|
||||
## المصدر
|
||||
- الكتاب: العلوم الحياتية - الصف العاشر - الفصل الدراسي الأول
|
||||
|
||||
@@ -6,14 +6,14 @@ unit_key: unit_01
|
||||
lesson_key: unit_review
|
||||
resource_type: unit_review
|
||||
curriculum_version: jordan-grade10-2026-source-review
|
||||
title: "مراجعة واختبار الوحدة الأولى: أنشطة الخلية"
|
||||
title: "مراجعة واختبار الوحدة الأولى: نظرية التطور"
|
||||
source:
|
||||
original_pdf: "كتاب الطالب لمادة العلوم الحياتية للصف العاشر الفصل الأول.pdf"
|
||||
pages: [18, 19]
|
||||
extraction_method: "text"
|
||||
extraction_review_status: "needs_human_review"
|
||||
extraction_review_status: "approved"
|
||||
---
|
||||
# مراجعة واختبار الوحدة الأولى: أنشطة الخلية
|
||||
# مراجعة واختبار الوحدة الأولى: نظرية التطور
|
||||
|
||||
## المصدر
|
||||
- الكتاب: العلوم الحياتية - الصف العاشر - الفصل الدراسي الأول
|
||||
|
||||
@@ -6,14 +6,14 @@ unit_key: unit_02
|
||||
lesson_key: lesson_01
|
||||
resource_type: lesson
|
||||
curriculum_version: jordan-grade10-2026-source-review
|
||||
title: "الدرس الأول: المادة الوراثية وتضاعف الحمض النووي DNA وبناء البروتين"
|
||||
title: "الدرس 1: الفيروسات (Viruses)"
|
||||
source:
|
||||
original_pdf: "كتاب الطالب لمادة العلوم الحياتية للصف العاشر الفصل الأول.pdf"
|
||||
pages: [20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 32, 33]
|
||||
extraction_method: "text"
|
||||
extraction_review_status: "needs_human_review"
|
||||
extraction_review_status: "approved"
|
||||
---
|
||||
# الدرس الأول: المادة الوراثية وتضاعف الحمض النووي DNA وبناء البروتين
|
||||
# الدرس 1: الفيروسات (Viruses)
|
||||
|
||||
## المصدر
|
||||
- الكتاب: العلوم الحياتية - الصف العاشر - الفصل الدراسي الأول
|
||||
|
||||
@@ -6,14 +6,14 @@ unit_key: unit_02
|
||||
lesson_key: unit_review
|
||||
resource_type: unit_review
|
||||
curriculum_version: jordan-grade10-2026-source-review
|
||||
title: "مراجعة واختبار الوحدة الثانية: الوراثة والبيولوجيا الجزيئية"
|
||||
title: "مراجعة واختبار الوحدة الثانية: الفيروسات والفيرويدات والبريونات"
|
||||
source:
|
||||
original_pdf: "كتاب الطالب لمادة العلوم الحياتية للصف العاشر الفصل الأول.pdf"
|
||||
pages: [34, 35]
|
||||
extraction_method: "text"
|
||||
extraction_review_status: "needs_human_review"
|
||||
extraction_review_status: "approved"
|
||||
---
|
||||
# مراجعة واختبار الوحدة الثانية: الوراثة والبيولوجيا الجزيئية
|
||||
# مراجعة واختبار الوحدة الثانية: الفيروسات والفيرويدات والبريونات
|
||||
|
||||
## المصدر
|
||||
- الكتاب: العلوم الحياتية - الصف العاشر - الفصل الدراسي الأول
|
||||
|
||||
@@ -1641,43 +1641,43 @@
|
||||
"name": "الفصل الدراسي الأول",
|
||||
"units": {
|
||||
"unit_01": {
|
||||
"name": "الوحدة الأولى",
|
||||
"name": "الوحدة الأولى: نظرية التطور (Evolution Theory)",
|
||||
"lessons": [
|
||||
{
|
||||
"id": "lesson_01",
|
||||
"title": "الدرس الأول: النقل عبر الغشاء البلازمي والخاصية الأسموزية والانتشار",
|
||||
"title": "الدرس: تطور الكائنات الحية (Living Organisms Evolution)",
|
||||
"file": "grade_10\/biology_10\/semester_1\/unit_01\/lesson_01.md",
|
||||
"outcomes": [
|
||||
"الدرس الأول: النقل عبر الغشاء البلازمي والخاصية الأسموزية والانتشار"
|
||||
"الدرس: تطور الكائنات الحية (Living Organisms Evolution)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "unit_review",
|
||||
"title": "مراجعة واختبار الوحدة الأولى: أنشطة الخلية",
|
||||
"title": "مراجعة واختبار الوحدة الأولى: نظرية التطور",
|
||||
"file": "grade_10\/biology_10\/semester_1\/unit_01\/unit_review.md",
|
||||
"outcomes": [
|
||||
"مراجعة واختبار الوحدة الأولى: أنشطة الخلية"
|
||||
"مراجعة واختبار الوحدة الأولى: نظرية التطور"
|
||||
]
|
||||
}
|
||||
]
|
||||
},
|
||||
"unit_02": {
|
||||
"name": "الوحدة الثانية",
|
||||
"name": "الوحدة الثانية: الفيروسات والفيرويدات والبريونات (Viruses, Viroids and Prions)",
|
||||
"lessons": [
|
||||
{
|
||||
"id": "lesson_01",
|
||||
"title": "الدرس الأول: المادة الوراثية وتضاعف الحمض النووي DNA وبناء البروتين",
|
||||
"title": "الدرس 1: الفيروسات (Viruses)",
|
||||
"file": "grade_10\/biology_10\/semester_1\/unit_02\/lesson_01.md",
|
||||
"outcomes": [
|
||||
"الدرس الأول: المادة الوراثية وتضاعف الحمض النووي DNA وبناء البروتين"
|
||||
"الدرس 1: الفيروسات (Viruses)"
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "unit_review",
|
||||
"title": "مراجعة واختبار الوحدة الثانية: الوراثة والبيولوجيا الجزيئية",
|
||||
"title": "مراجعة واختبار الوحدة الثانية: الفيروسات والفيرويدات والبريونات",
|
||||
"file": "grade_10\/biology_10\/semester_1\/unit_02\/unit_review.md",
|
||||
"outcomes": [
|
||||
"مراجعة واختبار الوحدة الثانية: الوراثة والبيولوجيا الجزيئية"
|
||||
"مراجعة واختبار الوحدة الثانية: الفيروسات والفيرويدات والبريونات"
|
||||
]
|
||||
}
|
||||
]
|
||||
|
||||
Reference in New Issue
Block a user