1
0
Fork 0
mirror of https://github.com/Eggbertx/gochan.git synced 2025-08-02 23:26:23 -07:00

Add PostJSON type for external rendering

This commit is contained in:
Eggbertx 2022-11-13 20:52:47 -08:00
parent 282ebe2280
commit 30b5a84aab
3 changed files with 156 additions and 31 deletions

View file

@ -1,7 +1,6 @@
package building
import (
"encoding/json"
"errors"
"fmt"
"io"
@ -118,36 +117,6 @@ func BuildFrontPage() error {
return nil
}
// BuildBoardListJSON generates a JSON file with info about the boards
func BuildBoardListJSON() error {
criticalCfg := config.GetSystemCriticalConfig()
boardListFile, err := os.OpenFile(path.Join(criticalCfg.DocumentRoot, "boards.json"), os.O_CREATE|os.O_RDWR|os.O_TRUNC, 0777)
if err != nil {
gcutil.LogError(err).
Str("building", "boardsList").Send()
return errors.New("Failed opening boards.json for writing: " + err.Error())
}
defer boardListFile.Close()
boardsMap := map[string][]gcsql.Board{
"boards": {},
}
// TODO: properly check if the board is in a hidden section
boardsMap["boards"] = gcsql.AllBoards
boardJSON, err := json.Marshal(boardsMap)
if err != nil {
gcutil.LogError(err).Str("building", "boards.json").Send()
return errors.New("Failed to create boards.json: " + err.Error())
}
if _, err = serverutil.MinifyWriter(boardListFile, boardJSON, "application/json"); err != nil {
gcutil.LogError(err).Str("building", "boards.json").Send()
return errors.New("Failed writing boards.json file: " + err.Error())
}
return nil
}
// BuildPageHeader is a convenience function for automatically generating the top part
// of every normal HTML page
func BuildPageHeader(writer io.Writer, pageTitle string, board string, misc map[string]interface{}) error {

127
pkg/building/json.go Normal file
View file

@ -0,0 +1,127 @@
package building
import (
"encoding/json"
"errors"
"os"
"path"
"strconv"
"github.com/gochan-org/gochan/pkg/config"
"github.com/gochan-org/gochan/pkg/gcsql"
"github.com/gochan-org/gochan/pkg/gcutil"
"github.com/gochan-org/gochan/pkg/serverutil"
)
const (
postQueryBase = `SELECT DBPREFIXposts.id AS postid, thread_id AS threadid, name, tripcode, email, subject,
(SELECT id FROM DBPREFIXposts WHERE thread_id = threadid AND is_top_post) AS parent_id,
(SELECT board_id FROM DBPREFIXthreads where id = threadid LIMIT 1) AS boardid,
(SELECT dir FROM DBPREFIXboards WHERE id = boardid LIMIT 1) AS dir,
coalesce(DBPREFIXfiles.original_filename,'') as original_filename,
coalesce(DBPREFIXfiles.filename,'') AS filename,
coalesce(DBPREFIXfiles.checksum,'') AS checksum,
coalesce(DBPREFIXfiles.file_size,0) AS filesize,
coalesce(DBPREFIXfiles.thumbnail_width,0) AS tw,
coalesce(DBPREFIXfiles.thumbnail_height,0) AS th,
coalesce(DBPREFIXfiles.width,0) AS width,
coalesce(DBPREFIXfiles.height,0) AS height
FROM DBPREFIXposts
LEFT JOIN DBPREFIXfiles ON DBPREFIXfiles.post_id = DBPREFIXposts.id WHERE is_deleted = 0`
)
type PostJSON struct {
ID int `json:"no"`
ParentID int `json:"resto"`
BoardID int `json:"-"`
BoardDir string `json:"-"`
Name string `json:"name"`
Trip string `json:"trip"`
Email string `json:"email"`
Subject string `json:"sub"`
Message string `json:"com"`
Filename string `json:"tim"`
OriginalFilename string `json:"filename"`
Checksum string `json:"md5"`
Extension string `json:"extension"`
Filesize int `json:"fsize"`
Width int `json:"w"`
Height int `json:"h"`
ThumbnailWidth int `json:"tn_w"`
ThumbnailHeight int `json:"tn_h"`
Capcode string `json:"capcode"`
Time string `json:"time"`
LastModified string `json:"last_modified"`
}
func GetPostJSON(id int, boardid int) (*PostJSON, error) {
const query = postQueryBase + " AND DBPREFIXposts.id = ?"
var post PostJSON
var threadID int
err := gcsql.QueryRowSQL(query, []interface{}{id}, []interface{}{
&post.ID, &threadID, &post.Name, &post.Trip, &post.Email, &post.Subject,
&post.ParentID, &post.BoardID, &post.BoardDir, &post.OriginalFilename, &post.Filename,
&post.Checksum, &post.Filesize, &post.ThumbnailWidth, &post.ThumbnailHeight,
&post.Width, &post.Height,
})
if err != nil {
return nil, err
}
return &post, nil
}
func GetRecentPosts(boardid int, limit int) ([]PostJSON, error) {
rows, err := gcsql.QuerySQL(postQueryBase + " LIMIT " + strconv.Itoa(limit))
if err != nil {
return nil, err
}
defer rows.Close()
var posts []PostJSON
for rows.Next() {
var post PostJSON
var threadID int
err = rows.Scan(
&post.ID, &threadID, &post.Name, &post.Trip, &post.Email, &post.Subject,
&post.ParentID, &post.BoardID, &post.BoardDir, &post.OriginalFilename, &post.Filename,
&post.Checksum, &post.Filesize, &post.ThumbnailWidth, &post.ThumbnailHeight,
&post.Width, &post.Height,
)
if err != nil {
return nil, err
}
if boardid > 0 && post.BoardID == boardid {
posts = append(posts, post)
}
}
return posts, nil
}
// BuildBoardListJSON generates a JSON file with info about the boards
func BuildBoardListJSON() error {
criticalCfg := config.GetSystemCriticalConfig()
boardListFile, err := os.OpenFile(path.Join(criticalCfg.DocumentRoot, "boards.json"), os.O_CREATE|os.O_RDWR|os.O_TRUNC, 0777)
if err != nil {
gcutil.LogError(err).
Str("building", "boardsList").Send()
return errors.New("Failed opening boards.json for writing: " + err.Error())
}
defer boardListFile.Close()
boardsMap := map[string][]gcsql.Board{
"boards": {},
}
// TODO: properly check if the board is in a hidden section
boardsMap["boards"] = gcsql.AllBoards
boardJSON, err := json.Marshal(boardsMap)
if err != nil {
gcutil.LogError(err).Str("building", "boards.json").Send()
return errors.New("Failed to create boards.json: " + err.Error())
}
if _, err = serverutil.MinifyWriter(boardListFile, boardJSON, "application/json"); err != nil {
gcutil.LogError(err).Str("building", "boards.json").Send()
return errors.New("Failed writing boards.json file: " + err.Error())
}
return nil
}

View file

@ -165,6 +165,35 @@ var actions = []Action{
}
return outputStr, nil
}},
{
ID: "recentposts",
Title: "Recent posts",
Permissions: JanitorPerms,
JSONoutput: OptionalJSON,
Callback: func(writer http.ResponseWriter, request *http.Request, staff *gcsql.Staff, wantsJSON bool, infoEv, errEv *zerolog.Event) (output interface{}, err error) {
limit, err := getIntField("limit", staff.Username, request, 0)
if err != nil {
return "", err
}
boardid, err := getIntField("boardid", staff.Username, request, 0)
if err != nil {
return "", err
}
recentposts, err := building.GetRecentPosts(boardid, limit)
if err != nil {
return "", err
}
manageRecentsBuffer := bytes.NewBufferString("")
if err = serverutil.MinifyTemplate(gctemplates.ManageRecentPosts, map[string]interface{}{
"recentposts": recentposts,
"webroot": config.GetSystemCriticalConfig().WebRoot,
}, manageRecentsBuffer, "text/html"); err != nil {
errEv.Err(err).Caller().Send()
return "", errors.New("Error executing ban management page template: " + err.Error())
}
return manageRecentsBuffer.String(), nil
},
},
// {
// ID: "recentposts",
// Title: "Recent posts",