Feat: word card repo
This commit is contained in:
		| @@ -24,7 +24,7 @@ CREATE TABLE players ( | |||||||
|     team TEXT NOT NULL DEFAULT '', -- 'red' or 'blue' |     team TEXT NOT NULL DEFAULT '', -- 'red' or 'blue' | ||||||
|     role TEXT NOT NULL DEFAULT '', -- 'guesser' or 'mime' |     role TEXT NOT NULL DEFAULT '', -- 'guesser' or 'mime' | ||||||
|     is_bot BOOLEAN NOT NULL DEFAULT FALSE, |     is_bot BOOLEAN NOT NULL DEFAULT FALSE, | ||||||
|     FOREIGN KEY (room_id) REFERENCES rooms(id) |     FOREIGN KEY (room_id) REFERENCES rooms(id) ON DELETE CASCADE | ||||||
| ); | ); | ||||||
|  |  | ||||||
| CREATE TABLE word_cards ( | CREATE TABLE word_cards ( | ||||||
| @@ -34,7 +34,7 @@ CREATE TABLE word_cards ( | |||||||
|     color TEXT NOT NULL DEFAULT '', |     color TEXT NOT NULL DEFAULT '', | ||||||
|     revealed BOOLEAN NOT NULL DEFAULT FALSE, |     revealed BOOLEAN NOT NULL DEFAULT FALSE, | ||||||
|     mime_view BOOLEAN NOT NULL DEFAULT FALSE, |     mime_view BOOLEAN NOT NULL DEFAULT FALSE, | ||||||
|     FOREIGN KEY (room_id) REFERENCES rooms(id) |     FOREIGN KEY (room_id) REFERENCES rooms(id) ON DELETE CASCADE | ||||||
| ); | ); | ||||||
|  |  | ||||||
| CREATE TABLE card_marks ( | CREATE TABLE card_marks ( | ||||||
| @@ -42,7 +42,7 @@ CREATE TABLE card_marks ( | |||||||
|     card_id INTEGER NOT NULL, |     card_id INTEGER NOT NULL, | ||||||
|     username TEXT NOT NULL, |     username TEXT NOT NULL, | ||||||
|     active BOOLEAN NOT NULL DEFAULT TRUE, |     active BOOLEAN NOT NULL DEFAULT TRUE, | ||||||
|     FOREIGN KEY (card_id) REFERENCES word_cards(id) |     FOREIGN KEY (card_id) REFERENCES word_cards(id) ON DELETE CASCADE | ||||||
| ); | ); | ||||||
|  |  | ||||||
| CREATE TABLE actions ( | CREATE TABLE actions ( | ||||||
| @@ -55,7 +55,7 @@ CREATE TABLE actions ( | |||||||
|     word_color TEXT NOT NULL DEFAULT '', |     word_color TEXT NOT NULL DEFAULT '', | ||||||
|     number_associated TEXT NOT NULL DEFAULT '', -- for clues |     number_associated TEXT NOT NULL DEFAULT '', -- for clues | ||||||
|     created_at TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP, |     created_at TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP, | ||||||
|     FOREIGN KEY (room_id) REFERENCES rooms(id) |     FOREIGN KEY (room_id) REFERENCES rooms(id) ON DELETE CASCADE | ||||||
| ); | ); | ||||||
|  |  | ||||||
| CREATE TABLE settings ( | CREATE TABLE settings ( | ||||||
| @@ -65,7 +65,7 @@ CREATE TABLE settings ( | |||||||
|     room_pass TEXT NOT NULL DEFAULT '', |     room_pass TEXT NOT NULL DEFAULT '', | ||||||
|     turn_time INTEGER NOT NULL DEFAULT 60, -- seconds |     turn_time INTEGER NOT NULL DEFAULT 60, -- seconds | ||||||
|     created_at TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP, |     created_at TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP, | ||||||
|     FOREIGN KEY (room_id) REFERENCES rooms(id) |     FOREIGN KEY (room_id) REFERENCES rooms(id) ON DELETE CASCADE | ||||||
| ); | ); | ||||||
|  |  | ||||||
| CREATE TABLE sessions( | CREATE TABLE sessions( | ||||||
| @@ -74,5 +74,5 @@ CREATE TABLE sessions( | |||||||
|     lifetime INTEGER NOT NULL DEFAULT 3600, |     lifetime INTEGER NOT NULL DEFAULT 3600, | ||||||
|     token_key TEXT NOT NULL DEFAULT '' UNIQUE, -- encoded value |     token_key TEXT NOT NULL DEFAULT '' UNIQUE, -- encoded value | ||||||
|     username TEXT NOT NULL, |     username TEXT NOT NULL, | ||||||
|     FOREIGN KEY (username) REFERENCES players(username) |     FOREIGN KEY (username) REFERENCES players(username) ON DELETE CASCADE | ||||||
| ); | ); | ||||||
| @@ -16,6 +16,7 @@ type AllRepos interface { | |||||||
| 	ActionsRepo | 	ActionsRepo | ||||||
| 	PlayersRepo | 	PlayersRepo | ||||||
| 	SessionsRepo | 	SessionsRepo | ||||||
|  | 	WordCardsRepo | ||||||
| } | } | ||||||
|  |  | ||||||
| type RepoProvider struct { | type RepoProvider struct { | ||||||
|   | |||||||
| @@ -53,10 +53,6 @@ func (p *RepoProvider) RoomCreate(ctx context.Context, r *models.Room) error { | |||||||
| func (p *RepoProvider) RoomDeleteByID(ctx context.Context, id string) error { | func (p *RepoProvider) RoomDeleteByID(ctx context.Context, id string) error { | ||||||
| 	db := getDB(ctx, p.DB) | 	db := getDB(ctx, p.DB) | ||||||
| 	_, err := db.ExecContext(ctx, `DELETE FROM rooms WHERE id = ?`, id) | 	_, err := db.ExecContext(ctx, `DELETE FROM rooms WHERE id = ?`, id) | ||||||
| 	if err != nil { |  | ||||||
| 		return err |  | ||||||
| 	} |  | ||||||
| 	_, err = db.ExecContext(ctx, `DELETE FROM settings WHERE room_id = ?`, id) |  | ||||||
| 	return err | 	return err | ||||||
| } | } | ||||||
|  |  | ||||||
|   | |||||||
| @@ -15,6 +15,10 @@ func setupTestDB(t *testing.T) (*sqlx.DB, func()) { | |||||||
| 	db, err := sqlx.Connect("sqlite3", ":memory:") | 	db, err := sqlx.Connect("sqlite3", ":memory:") | ||||||
| 	assert.NoError(t, err) | 	assert.NoError(t, err) | ||||||
|  |  | ||||||
|  | 	// Enable foreign key constraints for SQLite | ||||||
|  | 	_, err = db.Exec("PRAGMA foreign_keys = ON;") | ||||||
|  | 	assert.NoError(t, err) | ||||||
|  |  | ||||||
| 	schema := ` | 	schema := ` | ||||||
| 	CREATE TABLE IF NOT EXISTS rooms ( | 	CREATE TABLE IF NOT EXISTS rooms ( | ||||||
| 		id TEXT PRIMARY KEY, | 		id TEXT PRIMARY KEY, | ||||||
| @@ -33,6 +37,47 @@ func setupTestDB(t *testing.T) (*sqlx.DB, func()) { | |||||||
| 		room_link TEXT NOT NULL DEFAULT '' | 		room_link TEXT NOT NULL DEFAULT '' | ||||||
| 	); | 	); | ||||||
|  |  | ||||||
|  | 	CREATE TABLE IF NOT EXISTS players ( | ||||||
|  | 		id INTEGER PRIMARY KEY AUTOINCREMENT, | ||||||
|  | 		room_id TEXT, | ||||||
|  | 		username TEXT NOT NULL UNIQUE, | ||||||
|  | 		team TEXT NOT NULL DEFAULT '', | ||||||
|  | 		role TEXT NOT NULL DEFAULT '', | ||||||
|  | 		is_bot BOOLEAN NOT NULL DEFAULT FALSE, | ||||||
|  | 		FOREIGN KEY (room_id) REFERENCES rooms(id) ON DELETE CASCADE | ||||||
|  | 	); | ||||||
|  |  | ||||||
|  | 	CREATE TABLE IF NOT EXISTS word_cards ( | ||||||
|  | 		id INTEGER PRIMARY KEY AUTOINCREMENT, | ||||||
|  | 		room_id TEXT NOT NULL, | ||||||
|  | 		word TEXT NOT NULL, | ||||||
|  | 		color TEXT NOT NULL DEFAULT '', | ||||||
|  | 		revealed BOOLEAN NOT NULL DEFAULT FALSE, | ||||||
|  | 		mime_view BOOLEAN NOT NULL DEFAULT FALSE, | ||||||
|  | 		FOREIGN KEY (room_id) REFERENCES rooms(id) ON DELETE CASCADE | ||||||
|  | 	); | ||||||
|  |  | ||||||
|  | 	CREATE TABLE IF NOT EXISTS card_marks ( | ||||||
|  | 		id INTEGER PRIMARY KEY AUTOINCREMENT, | ||||||
|  | 		card_id INTEGER NOT NULL, | ||||||
|  | 		username TEXT NOT NULL, | ||||||
|  | 		active BOOLEAN NOT NULL DEFAULT TRUE, | ||||||
|  | 		FOREIGN KEY (card_id) REFERENCES word_cards(id) ON DELETE CASCADE | ||||||
|  | 	); | ||||||
|  |  | ||||||
|  | 	CREATE TABLE IF NOT EXISTS actions ( | ||||||
|  | 		id INTEGER PRIMARY KEY AUTOINCREMENT, | ||||||
|  | 		room_id TEXT NOT NULL, | ||||||
|  | 		actor TEXT NOT NULL, | ||||||
|  | 		actor_color TEXT NOT NULL DEFAULT '', | ||||||
|  | 		action_type TEXT NOT NULL, | ||||||
|  | 		word TEXT NOT NULL DEFAULT '', | ||||||
|  | 		word_color TEXT NOT NULL DEFAULT '', | ||||||
|  | 		number_associated TEXT NOT NULL DEFAULT '', | ||||||
|  | 		created_at TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP, | ||||||
|  | 		FOREIGN KEY (room_id) REFERENCES rooms(id) ON DELETE CASCADE | ||||||
|  | 	); | ||||||
|  |  | ||||||
| 	CREATE TABLE IF NOT EXISTS settings ( | 	CREATE TABLE IF NOT EXISTS settings ( | ||||||
| 		id INTEGER PRIMARY KEY AUTOINCREMENT, | 		id INTEGER PRIMARY KEY AUTOINCREMENT, | ||||||
| 		room_id TEXT NOT NULL, | 		room_id TEXT NOT NULL, | ||||||
| @@ -40,7 +85,16 @@ func setupTestDB(t *testing.T) (*sqlx.DB, func()) { | |||||||
| 		room_pass TEXT NOT NULL DEFAULT '', | 		room_pass TEXT NOT NULL DEFAULT '', | ||||||
| 		turn_time INTEGER NOT NULL DEFAULT 60, | 		turn_time INTEGER NOT NULL DEFAULT 60, | ||||||
| 		created_at TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP, | 		created_at TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP, | ||||||
| 		FOREIGN KEY (room_id) REFERENCES rooms(id) | 		FOREIGN KEY (room_id) REFERENCES rooms(id) ON DELETE CASCADE | ||||||
|  | 	); | ||||||
|  |  | ||||||
|  | 	CREATE TABLE IF NOT EXISTS sessions( | ||||||
|  | 		id INTEGER PRIMARY KEY AUTOINCREMENT, | ||||||
|  | 		updated_at TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP, | ||||||
|  | 		lifetime INTEGER NOT NULL DEFAULT 3600, | ||||||
|  | 		token_key TEXT NOT NULL DEFAULT '' UNIQUE, | ||||||
|  | 		username TEXT NOT NULL, | ||||||
|  | 		FOREIGN KEY (username) REFERENCES players(username) ON DELETE CASCADE | ||||||
| 	); | 	); | ||||||
| 	` | 	` | ||||||
| 	_, err = db.Exec(schema) | 	_, err = db.Exec(schema) | ||||||
| @@ -236,6 +290,17 @@ func TestRoomsRepo_DeleteRoomByID(t *testing.T) { | |||||||
| 	_, err = db.Exec(`INSERT INTO settings (room_id, language, room_pass, turn_time) VALUES (?, ?, ?, ?)`, room.ID, room.Settings.Language, room.Settings.RoomPass, room.Settings.RoundTime) | 	_, err = db.Exec(`INSERT INTO settings (room_id, language, room_pass, turn_time) VALUES (?, ?, ?, ?)`, room.ID, room.Settings.Language, room.Settings.RoomPass, room.Settings.RoundTime) | ||||||
| 	assert.NoError(t, err) | 	assert.NoError(t, err) | ||||||
|  |  | ||||||
|  | 	// Insert a word card for the room | ||||||
|  | 	wordCard := &models.WordCard{ | ||||||
|  | 		RoomID:   room.ID, | ||||||
|  | 		Word:     "test_word", | ||||||
|  | 		Color:    models.WordColorBlue, | ||||||
|  | 		Revealed: false, | ||||||
|  | 		Mime:     false, | ||||||
|  | 	} | ||||||
|  | 	_, err = db.Exec(`INSERT INTO word_cards (room_id, word, color, revealed, mime_view) VALUES (?, ?, ?, ?, ?)`, wordCard.RoomID, wordCard.Word, wordCard.Color, wordCard.Revealed, wordCard.Mime) | ||||||
|  | 	assert.NoError(t, err) | ||||||
|  |  | ||||||
| 	err = repo.RoomDeleteByID(context.Background(), room.ID) | 	err = repo.RoomDeleteByID(context.Background(), room.ID) | ||||||
| 	assert.NoError(t, err) | 	assert.NoError(t, err) | ||||||
|  |  | ||||||
| @@ -247,6 +312,10 @@ func TestRoomsRepo_DeleteRoomByID(t *testing.T) { | |||||||
| 	err = db.Get(&count, "SELECT COUNT(*) FROM settings WHERE room_id = ?", room.ID) | 	err = db.Get(&count, "SELECT COUNT(*) FROM settings WHERE room_id = ?", room.ID) | ||||||
| 	assert.NoError(t, err) | 	assert.NoError(t, err) | ||||||
| 	assert.Equal(t, 0, count) | 	assert.Equal(t, 0, count) | ||||||
|  |  | ||||||
|  | 	err = db.Get(&count, "SELECT COUNT(*) FROM word_cards WHERE room_id = ?", room.ID) | ||||||
|  | 	assert.NoError(t, err) | ||||||
|  | 	assert.Equal(t, 0, count) | ||||||
| } | } | ||||||
|  |  | ||||||
| func TestRoomsRepo_UpdateRoom(t *testing.T) { | func TestRoomsRepo_UpdateRoom(t *testing.T) { | ||||||
|   | |||||||
							
								
								
									
										59
									
								
								repos/word_cards.go
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										59
									
								
								repos/word_cards.go
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,59 @@ | |||||||
|  | package repos | ||||||
|  |  | ||||||
|  | import ( | ||||||
|  | 	"context" | ||||||
|  | 	"gralias/models" | ||||||
|  |  | ||||||
|  | 	"github.com/jmoiron/sqlx" | ||||||
|  | ) | ||||||
|  |  | ||||||
|  | type WordCardsRepo interface { | ||||||
|  | 	WordCardsCreate(ctx context.Context, card *models.WordCard) error | ||||||
|  | 	WordCardsGetByRoomID(ctx context.Context, roomID string) ([]models.WordCard, error) | ||||||
|  | 	WordCardGetByWordAndRoomID(ctx context.Context, word, roomID string) (*models.WordCard, error) | ||||||
|  | 	WordCardReveal(ctx context.Context, word, roomID string) error | ||||||
|  | 	WordCardsRevealAll(ctx context.Context, roomID string) error | ||||||
|  | 	WordCardsDeleteByRoomID(ctx context.Context, roomID string) error | ||||||
|  | } | ||||||
|  |  | ||||||
|  | func (p *RepoProvider) WordCardsCreate(ctx context.Context, card *models.WordCard) error { | ||||||
|  | 	db := getDB(ctx, p.DB) | ||||||
|  | 	_, err := db.ExecContext(ctx, `INSERT INTO word_cards (room_id, word, color, revealed, mime_view) VALUES (?, ?, ?, ?, ?)`, card.RoomID, card.Word, card.Color, card.Revealed, card.Mime) | ||||||
|  | 	return err | ||||||
|  | } | ||||||
|  |  | ||||||
|  | func (p *RepoProvider) WordCardsGetByRoomID(ctx context.Context, roomID string) ([]models.WordCard, error) { | ||||||
|  | 	cards := []models.WordCard{} | ||||||
|  | 	err := sqlx.SelectContext(ctx, p.DB, &cards, `SELECT * FROM word_cards WHERE room_id = ?`, roomID) | ||||||
|  | 	if err != nil { | ||||||
|  | 		return nil, err | ||||||
|  | 	} | ||||||
|  | 	return cards, nil | ||||||
|  | } | ||||||
|  |  | ||||||
|  | func (p *RepoProvider) WordCardGetByWordAndRoomID(ctx context.Context, word, roomID string) (*models.WordCard, error) { | ||||||
|  | 	card := &models.WordCard{} | ||||||
|  | 	err := sqlx.GetContext(ctx, p.DB, card, `SELECT * FROM word_cards WHERE word = ? AND room_id = ?`, word, roomID) | ||||||
|  | 	if err != nil { | ||||||
|  | 		return nil, err | ||||||
|  | 	} | ||||||
|  | 	return card, nil | ||||||
|  | } | ||||||
|  |  | ||||||
|  | func (p *RepoProvider) WordCardReveal(ctx context.Context, word, roomID string) error { | ||||||
|  | 	db := getDB(ctx, p.DB) | ||||||
|  | 	_, err := db.ExecContext(ctx, `UPDATE word_cards SET revealed = TRUE WHERE word = ? AND room_id = ?`, word, roomID) | ||||||
|  | 	return err | ||||||
|  | } | ||||||
|  |  | ||||||
|  | func (p *RepoProvider) WordCardsRevealAll(ctx context.Context, roomID string) error { | ||||||
|  | 	db := getDB(ctx, p.DB) | ||||||
|  | 	_, err := db.ExecContext(ctx, `UPDATE word_cards SET revealed = TRUE WHERE room_id = ?`, roomID) | ||||||
|  | 	return err | ||||||
|  | } | ||||||
|  |  | ||||||
|  | func (p *RepoProvider) WordCardsDeleteByRoomID(ctx context.Context, roomID string) error { | ||||||
|  | 	db := getDB(ctx, p.DB) | ||||||
|  | 	_, err := db.ExecContext(ctx, `DELETE FROM word_cards WHERE room_id = ?`, roomID) | ||||||
|  | 	return err | ||||||
|  | } | ||||||
		Reference in New Issue
	
	Block a user
	 Grail Finder
					Grail Finder