82 lines
2.0 KiB
Go
82 lines
2.0 KiB
Go
|
|
package routes
|
||
|
|
|
||
|
|
import (
|
||
|
|
"gifuu/tools"
|
||
|
|
"net/http"
|
||
|
|
)
|
||
|
|
|
||
|
|
func GET_Art_Search(w http.ResponseWriter, r *http.Request) {
|
||
|
|
ctx := r.Context()
|
||
|
|
query := r.URL.Query()
|
||
|
|
|
||
|
|
paramLimit := tools.ParseLimit(query.Get("limit"))
|
||
|
|
paramAfter := tools.ParseSnowflake(query.Get("after"))
|
||
|
|
var paramTags []int64
|
||
|
|
|
||
|
|
if params, ok := query["tag"]; ok {
|
||
|
|
paramTags = make([]int64, 0, len(params))
|
||
|
|
indexTags := make(map[int64]struct{}, len(params))
|
||
|
|
for _, raw := range params {
|
||
|
|
id := tools.ParseSnowflake(raw)
|
||
|
|
if _, exists := indexTags[id]; exists || id == 0 {
|
||
|
|
tools.SendClientError(w, r, tools.ERROR_BODY_INVALID_FIELD)
|
||
|
|
return
|
||
|
|
}
|
||
|
|
indexTags[id] = struct{}{}
|
||
|
|
paramTags = append(paramTags, id)
|
||
|
|
}
|
||
|
|
}
|
||
|
|
if len(paramTags) == 0 {
|
||
|
|
tools.SendClientError(w, r, tools.ERROR_BODY_EMPTY)
|
||
|
|
return
|
||
|
|
}
|
||
|
|
|
||
|
|
var Results []byte
|
||
|
|
err := tools.Database.QueryRow(ctx,
|
||
|
|
`SELECT COALESCE(jsonb_agg(t.obj), '[]') FROM (
|
||
|
|
SELECT jsonb_build_object(
|
||
|
|
'id', u.id::text,
|
||
|
|
'created', u.created::timestamptz,
|
||
|
|
'sticker', u.flag_sticker,
|
||
|
|
'audio', u.flag_audio,
|
||
|
|
'framerate', u.encode_fps,
|
||
|
|
'width', u.encode_width,
|
||
|
|
'height', u.encode_height,
|
||
|
|
'rating', u.meta_rating,
|
||
|
|
'title', u.meta_title,
|
||
|
|
'tags', COALESCE(
|
||
|
|
jsonb_agg(
|
||
|
|
jsonb_build_object(
|
||
|
|
'id', t.id::text,
|
||
|
|
'label', t.label,
|
||
|
|
'usage', t.usage
|
||
|
|
)
|
||
|
|
ORDER BY t.usage DESC
|
||
|
|
) FILTER (WHERE t.id IS NOT NULL),
|
||
|
|
'[]'
|
||
|
|
)
|
||
|
|
) AS obj
|
||
|
|
FROM gifuu.upload u
|
||
|
|
LEFT JOIN gifuu.upload_tag ut ON ut.gif_id = u.id
|
||
|
|
LEFT JOIN gifuu.tag t ON t.id = ut.tag_id
|
||
|
|
WHERE ut.tag_id = ANY($1::bigint[])
|
||
|
|
AND ($2::bigint = 0 OR u.id < $2::bigint)
|
||
|
|
AND u.meta_rating < $4
|
||
|
|
GROUP BY u.id
|
||
|
|
HAVING COUNT(DISTINCT ut.tag_id) = cardinality($1::bigint[])
|
||
|
|
ORDER BY u.id DESC
|
||
|
|
LIMIT $3::int
|
||
|
|
) t`,
|
||
|
|
paramTags,
|
||
|
|
paramAfter,
|
||
|
|
paramLimit,
|
||
|
|
tools.MODEL_THRESHOLD_HIDE,
|
||
|
|
).Scan(&Results)
|
||
|
|
if err != nil {
|
||
|
|
tools.SendServerError(w, r, err)
|
||
|
|
return
|
||
|
|
}
|
||
|
|
|
||
|
|
tools.SendJSON(w, r, http.StatusOK, Results)
|
||
|
|
}
|