diff options
| author | Paul Buetow <paul@buetow.org> | 2026-05-17 14:59:07 +0300 |
|---|---|---|
| committer | Paul Buetow <paul@buetow.org> | 2026-05-17 14:59:07 +0300 |
| commit | 3d2009bff0edddb413819ea542678738fb63cc0c (patch) | |
| tree | 53a8679920b0a3b1bc7598979c67492b51ea5fe6 /internal | |
| parent | dd3a961436868c32585b201b2da2dd5be23d609c (diff) | |
Add finished flag to playback progress
Diffstat (limited to 'internal')
| -rw-r--r-- | internal/model/media.go | 1 | ||||
| -rw-r--r-- | internal/model/media_test.go | 2 | ||||
| -rw-r--r-- | internal/repository/playback_progress.go | 12 | ||||
| -rw-r--r-- | internal/repository/schema.go | 1 | ||||
| -rw-r--r-- | internal/repository/sqlite_test.go | 8 |
5 files changed, 16 insertions, 8 deletions
diff --git a/internal/model/media.go b/internal/model/media.go index 48ab487..39ae4fd 100644 --- a/internal/model/media.go +++ b/internal/model/media.go @@ -121,6 +121,7 @@ type PlaybackProgress struct { UserID int64 `json:"user_id"` MediaID int64 `json:"media_id"` PositionSeconds float64 `json:"position_seconds"` + Finished bool `json:"finished"` UpdatedAt time.Time `json:"updated_at"` } diff --git a/internal/model/media_test.go b/internal/model/media_test.go index 49d877c..1692698 100644 --- a/internal/model/media_test.go +++ b/internal/model/media_test.go @@ -15,7 +15,7 @@ func TestStructsInstantiate(t *testing.T) { max := 1 _ = Share{Token: "t", MediaID: 1, CreatedBy: 1, CreatedAt: now, ExpiresAt: now, MaxUses: &max} _ = Note{ID: 1, MediaID: 1, UserID: 1, Content: "c", CreatedAt: now, UpdatedAt: now} - _ = PlaybackProgress{UserID: 1, MediaID: 1, PositionSeconds: 1, UpdatedAt: now} + _ = PlaybackProgress{UserID: 1, MediaID: 1, PositionSeconds: 1, Finished: true, UpdatedAt: now} _ = PlaybackAccumulator{SessionID: "s", MediaID: 1, UpdatedAt: now} _ = Favorite{UserID: 1, MediaID: 1, CreatedAt: now} _ = MediaTag{MediaID: 1, TagID: 1} diff --git a/internal/repository/playback_progress.go b/internal/repository/playback_progress.go index e628388..046598a 100644 --- a/internal/repository/playback_progress.go +++ b/internal/repository/playback_progress.go @@ -11,8 +11,8 @@ import ( // UpsertProgress inserts or replaces playback progress. func (s *SQLite) UpsertProgress(ctx context.Context, progress *model.PlaybackProgress) error { _, err := s.db.ExecContext(ctx, - `INSERT OR REPLACE INTO playback_progress (user_id, media_id, position_seconds, updated_at) VALUES (?, ?, ?, ?)`, - progress.UserID, progress.MediaID, progress.PositionSeconds, progress.UpdatedAt, + `INSERT OR REPLACE INTO playback_progress (user_id, media_id, position_seconds, finished, updated_at) VALUES (?, ?, ?, ?, ?)`, + progress.UserID, progress.MediaID, progress.PositionSeconds, progress.Finished, progress.UpdatedAt, ) if err != nil { return fmt.Errorf("upsert progress: %w", err) @@ -23,11 +23,11 @@ func (s *SQLite) UpsertProgress(ctx context.Context, progress *model.PlaybackPro // GetProgress retrieves playback progress for a user and media. func (s *SQLite) GetProgress(ctx context.Context, userID, mediaID int64) (*model.PlaybackProgress, error) { row := s.db.QueryRowContext(ctx, - `SELECT user_id, media_id, position_seconds, updated_at FROM playback_progress WHERE user_id = ? AND media_id = ?`, + `SELECT user_id, media_id, position_seconds, finished, updated_at FROM playback_progress WHERE user_id = ? AND media_id = ?`, userID, mediaID, ) var p model.PlaybackProgress - if err := row.Scan(&p.UserID, &p.MediaID, &p.PositionSeconds, &p.UpdatedAt); err == sql.ErrNoRows { + if err := row.Scan(&p.UserID, &p.MediaID, &p.PositionSeconds, &p.Finished, &p.UpdatedAt); err == sql.ErrNoRows { return nil, nil } else if err != nil { return nil, err @@ -38,7 +38,7 @@ func (s *SQLite) GetProgress(ctx context.Context, userID, mediaID int64) (*model // ListProgressByUser returns all progress records for a user. func (s *SQLite) ListProgressByUser(ctx context.Context, userID int64) ([]model.PlaybackProgress, error) { rows, err := s.db.QueryContext(ctx, - `SELECT user_id, media_id, position_seconds, updated_at FROM playback_progress WHERE user_id = ? ORDER BY updated_at DESC`, userID) + `SELECT user_id, media_id, position_seconds, finished, updated_at FROM playback_progress WHERE user_id = ? ORDER BY updated_at DESC`, userID) if err != nil { return nil, fmt.Errorf("list progress: %w", err) } @@ -46,7 +46,7 @@ func (s *SQLite) ListProgressByUser(ctx context.Context, userID int64) ([]model. var pp []model.PlaybackProgress for rows.Next() { var p model.PlaybackProgress - if err := rows.Scan(&p.UserID, &p.MediaID, &p.PositionSeconds, &p.UpdatedAt); err != nil { + if err := rows.Scan(&p.UserID, &p.MediaID, &p.PositionSeconds, &p.Finished, &p.UpdatedAt); err != nil { return nil, err } pp = append(pp, p) diff --git a/internal/repository/schema.go b/internal/repository/schema.go index a07f4ed..a49dbb7 100644 --- a/internal/repository/schema.go +++ b/internal/repository/schema.go @@ -83,6 +83,7 @@ CREATE TABLE IF NOT EXISTS playback_progress ( user_id INTEGER NOT NULL REFERENCES users(id) ON DELETE CASCADE, media_id INTEGER NOT NULL REFERENCES media(id) ON DELETE CASCADE, position_seconds REAL NOT NULL, + finished BOOLEAN NOT NULL DEFAULT 0, updated_at DATETIME DEFAULT CURRENT_TIMESTAMP, PRIMARY KEY (user_id, media_id) ); diff --git a/internal/repository/sqlite_test.go b/internal/repository/sqlite_test.go index a295fa4..bbe1330 100644 --- a/internal/repository/sqlite_test.go +++ b/internal/repository/sqlite_test.go @@ -464,7 +464,7 @@ func TestSQLite_PlaybackProgressRepo(t *testing.T) { uid, _ := s.CreateUser(ctx, &model.User{Username: "u", PasswordHash: "h", CreatedAt: now}) sid, _ := s.CreateSet(ctx, &model.Set{Name: "s", RootPath: "/s", CreatedAt: now}) mid, _ := s.CreateMedia(ctx, &model.Media{SetID: sid, RelPath: "a.mp4", FileName: "a.mp4", AbsPath: "/s/a.mp4", Type: model.MediaTypeVideo, CreatedAt: now}) - if err := s.UpsertProgress(ctx, &model.PlaybackProgress{UserID: uid, MediaID: mid, PositionSeconds: 42, UpdatedAt: now}); err != nil { + if err := s.UpsertProgress(ctx, &model.PlaybackProgress{UserID: uid, MediaID: mid, PositionSeconds: 42, Finished: true, UpdatedAt: now}); err != nil { t.Fatalf("upsert: %v", err) } p, err := s.GetProgress(ctx, uid, mid) @@ -474,10 +474,16 @@ func TestSQLite_PlaybackProgressRepo(t *testing.T) { if p.PositionSeconds != 42 { t.Fatalf("expected 42, got %f", p.PositionSeconds) } + if !p.Finished { + t.Fatal("expected finished") + } pp, _ := s.ListProgressByUser(ctx, uid) if len(pp) != 1 { t.Fatalf("expected 1, got %d", len(pp)) } + if !pp[0].Finished { + t.Fatal("expected listed progress to be finished") + } }, }, } |
