feat(lessons): ListVideos — плоский endpoint для раздела «Видео-уроки»
All checks were successful
CI / test (push) Successful in 19s
Build and Deploy / build-and-deploy (push) Successful in 26s

LessonRepository.ListVideos: SELECT с INNER JOIN courses, фильтр
video_key != '' + (course.is_published OR course.owner_user_id = viewer).
Возвращает LessonWithCourse — урок + denorm course_{title,slug,
is_published,owner_user_id} чтобы фронт сгруппировал по курсу
без N+1.

LessonHandler.ListVideos: GET /lessons?has_video=true. Гейт уже на
SQL-уровне, в коде только X-User-Id из headers.

Route регистрируется ДО /lessons/{id}, иначе chi бы заматчил
{id}="lessons".

Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
This commit is contained in:
Ilya
2026-05-26 00:17:34 +03:00
parent 80c019b791
commit 400df0124d
3 changed files with 70 additions and 0 deletions

View File

@@ -123,6 +123,10 @@ func main() {
r.Get("/courses/{courseId}/lessons", lessonH.ListByCourse)
r.Post("/courses/{courseId}/lessons", lessonH.Create)
r.Post("/courses/{courseId}/lessons/reorder", lessonH.Reorder)
// Flat-список уроков с видео для отдельной страницы «Видео-уроки».
// has_video=true игнорируется — у нас только этот режим; флаг
// зарезервирован для будущего фильтра «и без видео тоже».
r.Get("/lessons", lessonH.ListVideos)
r.Get("/lessons/{id}", lessonH.Get)
r.Patch("/lessons/{id}", lessonH.Update)
r.Delete("/lessons/{id}", lessonH.Delete)