From 658ee0f41d0cfba8d1e3fc52b11c12188baa1279 Mon Sep 17 00:00:00 2001 From: Eggbertx Date: Sun, 20 Oct 2024 01:01:13 -0700 Subject: [PATCH] Fix some issues with views (not getting the expected data, columns not matching, etc) --- pkg/building/boards.go | 2 +- pkg/building/catalog.go | 2 +- pkg/building/threads.go | 5 +++-- pkg/gcsql/posts.go | 37 ++++++++++++++++++++++--------------- pkg/gcsql/util.go | 6 ++++++ sql/reset_views.sql | 20 ++++++++++---------- 6 files changed, 43 insertions(+), 29 deletions(-) diff --git a/pkg/building/boards.go b/pkg/building/boards.go index 2b8d9401..4cbced43 100644 --- a/pkg/building/boards.go +++ b/pkg/building/boards.go @@ -525,7 +525,7 @@ func buildBoard(board *gcsql.Board, force bool) error { if err = BuildBoardPages(board, errEv); err != nil { return err } - if err = BuildThreads(true, board.ID, 0); err != nil { + if err = BuildThreads(true, board.Dir, 0); err != nil { errEv.Err(err).Caller().Send() return err } diff --git a/pkg/building/catalog.go b/pkg/building/catalog.go index f90ff475..506be032 100644 --- a/pkg/building/catalog.go +++ b/pkg/building/catalog.go @@ -63,7 +63,7 @@ func (catalog *boardCatalog) fillPages(threadsPerPage int, threads []catalogThre } func getBoardTopPosts(board string) ([]*Post, error) { - const query = "SELECT * FROM DBPREFIXv_board_top_posts WHERE DIR = ?" + const query = "SELECT * FROM DBPREFIXv_building_posts WHERE id = parent_id AND dir = ?" var posts []*Post err := QueryPosts(query, []any{board}, func(p *Post) error { diff --git a/pkg/building/threads.go b/pkg/building/threads.go index fab082e5..a7bfd292 100644 --- a/pkg/building/threads.go +++ b/pkg/building/threads.go @@ -18,11 +18,11 @@ import ( // BuildThreads builds thread(s) given a boardid, or if all = false, also given a threadid. // if all is set to true, ignore which, otherwise, which = build only specified boardid // TODO: make it variadic -func BuildThreads(all bool, boardid, threadid int) error { +func BuildThreads(all bool, board string, threadid int) error { var threads []*gcsql.Post var err error if all { - threads, err = gcsql.GetBoardTopPosts(boardid) + threads, err = gcsql.GetBoardTopPosts(board) } else { var post *gcsql.Post post, err = gcsql.GetThreadTopPost(threadid) @@ -91,6 +91,7 @@ func BuildThreadPages(op *gcsql.Post) error { errEv.Err(err).Caller().Send() return fmt.Errorf("unable to set file permissions for /%s/res/%d.html: %s", board.Dir, op.ID, err.Error()) } + fmt.Println(thread.ID, thread.BoardID) errEv.Int("op", posts[0].ID) // render thread page diff --git a/pkg/gcsql/posts.go b/pkg/gcsql/posts.go index 1613a70e..2c44cc70 100644 --- a/pkg/gcsql/posts.go +++ b/pkg/gcsql/posts.go @@ -139,31 +139,38 @@ func GetThreadTopPost(threadID int) (*Post, error) { return post, err } -func GetBoardTopPosts(boardID int) ([]*Post, error) { - const query = `SELECT * FROM DBPREFIXv_board_top_posts WHERE t.board_id = ?` - - rows, err := QuerySQL(query, boardID) +// GetBoardTopPosts gets the top posts of the given +func GetBoardTopPosts[B intOrStringConstraint](board B) ([]*Post, error) { + query := `SELECT id, thread_id, is_top_post, ip, created_on, name, tripcode, is_role_signature, + email, subject, message, message_raw, password, deleted_at, is_deleted, coalesce(banned_message,''), + flag, country + FROM DBPREFIXv_post_with_board WHERE is_top_post AND is_deleted = FALSE` + switch any(board).(type) { + case int: + query += " AND id = ?" + case string: + query += " AND dir = ?" + } + + rows, cancel, err := QueryTimeoutSQL(nil, query, board) if err != nil { return nil, err } - defer rows.Close() + defer func() { + rows.Close() + cancel() + }() var posts []*Post for rows.Next() { var post Post - // var tmp int // only needed for WHERE clause in query - - bannedMessage := new(string) - err = rows.Scan( + if err = rows.Scan( &post.ID, &post.ThreadID, &post.IsTopPost, &post.IP, &post.CreatedOn, &post.Name, &post.Tripcode, &post.IsRoleSignature, &post.Email, &post.Subject, &post.Message, - &post.MessageRaw, &post.Password, &post.DeletedAt, &post.IsDeleted, &bannedMessage, - ) - if err != nil { + &post.MessageRaw, &post.Password, &post.DeletedAt, &post.IsDeleted, &post.BannedMessage, + &post.Flag, &post.Country, + ); err != nil { return posts, err } - if bannedMessage != nil { - post.BannedMessage = *bannedMessage - } posts = append(posts, &post) } return posts, nil diff --git a/pkg/gcsql/util.go b/pkg/gcsql/util.go index fbdd19e9..bee04275 100644 --- a/pkg/gcsql/util.go +++ b/pkg/gcsql/util.go @@ -45,6 +45,12 @@ func (af BooleanFilter) whereClause(columnName string, and bool) string { return "" } +// intOrStringConstraint can be used to make using/creating query functions easier and to reduce the amount of reused code +// i.e., so we don't need GetPostsOnBoardByID() and GetPostsOnBoardByDir() +type intOrStringConstraint interface { + int | string +} + // BeginTx begins a new transaction for the gochan database. It uses a background context func BeginTx() (*sql.Tx, error) { return BeginContextTx(context.Background()) diff --git a/sql/reset_views.sql b/sql/reset_views.sql index 152a2970..b0093295 100644 --- a/sql/reset_views.sql +++ b/sql/reset_views.sql @@ -1,9 +1,9 @@ -- SQL views for simplifying queries in gochan -- First drop views if they exist in reverse order to avoid dependency issues +DROP VIEW IF EXISTS DBPREFIXv_post_with_board; DROP VIEW IF EXISTS DBPREFIXv_top_post_board_dir; DROP VIEW IF EXISTS DBPREFIXv_upload_info; -DROP VIEW IF EXISTS DBPREFIXv_board_top_posts; DROP VIEW IF EXISTS DBPREFIXv_front_page_posts_with_file; DROP VIEW IF EXISTS DBPREFIXv_front_page_posts; DROP VIEW IF EXISTS DBPREFIXv_posts_to_delete_file_only; @@ -85,14 +85,6 @@ SELECT * FROM DBPREFIXv_front_page_posts WHERE filename IS NOT NULL AND filename <> '' AND filename <> 'deleted'; -CREATE VIEW DBPREFIXv_board_top_posts AS -SELECT DBPREFIXposts.id, thread_id, is_top_post, ip, created_on, name, -tripcode, is_role_signature, email, subject, message, message_raw, -password, deleted_at, is_deleted, banned_message -FROM DBPREFIXposts -LEFT JOIN DBPREFIXv_thread_board_ids t on t.id = DBPREFIXposts.thread_id -WHERE is_deleted = FALSE AND is_top_post; - CREATE VIEW DBPREFIXv_upload_info AS SELECT p1.id as id, (SELECT id FROM DBPREFIXposts p2 WHERE p2.is_top_post AND p1.thread_id = p2.thread_id LIMIT 1) AS op, filename, is_spoilered, width, height, thumbnail_width, thumbnail_height @@ -106,4 +98,12 @@ CREATE VIEW DBPREFIXv_top_post_board_dir AS SELECT op.id, (SELECT dir FROM DBPREFIXboards WHERE id = t.board_id) AS dir FROM DBPREFIXposts LEFT JOIN DBPREFIXv_thread_board_ids t ON t.id = DBPREFIXposts.thread_id -INNER JOIN DBPREFIXv_top_post_thread_ids op on op.thread_id = DBPREFIXposts.thread_id; \ No newline at end of file +INNER JOIN DBPREFIXv_top_post_thread_ids op on op.thread_id = DBPREFIXposts.thread_id; + +CREATE VIEW DBPREFIXv_post_with_board AS +SELECT p.id AS id, thread_id, is_top_post, created_on, name, tripcode, is_role_signature, email, +subject, message, message_raw, password, p.deleted_at AS deleted_at, p.is_deleted AS is_deleted, +banned_message, ip, flag, country, dir, board_id +FROM DBPREFIXposts p +LEFT JOIN DBPREFIXthreads t ON t.id = p.thread_id +LEFT JOIN DBPREFIXboards b ON b.id = t.board_id;