offline-twitter/pkg/persistence/space_queries.go

85 lines
2.9 KiB
Go

package persistence
import (
"database/sql"
"errors"
"fmt"
. "gitlab.com/offline-twitter/twitter_offline_engine/pkg/scraper"
)
type SpaceParticipant struct {
UserID UserID `db:"user_id"`
SpaceID SpaceID `db:"space_id"`
}
// Save a Space
func (p Profile) SaveSpace(s Space) error {
_, err := p.DB.NamedExec(`
insert into spaces (id, created_by_id, short_url, state, title, created_at, started_at, ended_at, updated_at,
is_available_for_replay, replay_watch_count, live_listeners_count, is_details_fetched)
values (:id, nullif(:created_by_id, 0), :short_url, :state, :title, :created_at, :started_at, :ended_at, :updated_at,
:is_available_for_replay, :replay_watch_count, :live_listeners_count, :is_details_fetched)
on conflict do update
set id=:id,
created_by_id=case when created_by_id is not null then created_by_id else nullif(:created_by_id, 0) end,
short_url=case when short_url == '' then :short_url else short_url end,
state=case when :state != '' then :state else state end,
title=case when :is_details_fetched then :title else title end,
updated_at=max(:updated_at, updated_at),
ended_at=max(:ended_at, ended_at),
is_available_for_replay=:is_available_for_replay,
replay_watch_count=:replay_watch_count,
live_listeners_count=max(:live_listeners_count, live_listeners_count),
is_details_fetched=(is_details_fetched or :is_details_fetched)
`, &s)
if err != nil {
return fmt.Errorf("Error saving space (space ID %q, value: %#v):\n %w", s.ID, s, err)
}
space_participants := []SpaceParticipant{}
for _, participant_id := range s.ParticipantIds {
space_participants = append(space_participants, SpaceParticipant{UserID: participant_id, SpaceID: s.ID})
}
if len(space_participants) > 0 {
_, err = p.DB.NamedExec(`
insert or replace into space_participants (user_id, space_id) values (:user_id, :space_id)
`, space_participants)
if err != nil {
return fmt.Errorf("Error saving participants (space ID %q, participants: %#v):\n %w", s.ID, space_participants, err)
}
}
return nil
}
// Get a Space by ID
func (p Profile) GetSpaceById(id SpaceID) (space Space, err error) {
err = p.DB.Get(&space,
`select id, ifnull(created_by_id, 0) created_by_id, short_url, state, title, created_at, started_at, ended_at, updated_at,
is_available_for_replay, replay_watch_count, live_listeners_count, is_details_fetched
from spaces
where id = ?`, id)
if err != nil {
return
}
space.ParticipantIds = []UserID{}
rows, err := p.DB.Query(`select user_id from space_participants where space_id = ?`, id)
if errors.Is(err, sql.ErrNoRows) {
err = nil
}
defer rows.Close()
if err != nil {
panic(err)
}
var participant_id UserID
for rows.Next() {
err = rows.Scan(&participant_id)
if err != nil {
panic(err)
}
space.ParticipantIds = append(space.ParticipantIds, participant_id)
}
return
}