diff --git a/api/devices_list.go b/api/devices_list.go index 42777a1..eba0dc6 100644 --- a/api/devices_list.go +++ b/api/devices_list.go @@ -46,6 +46,8 @@ func (dlp DevicesListParams) Query() (expr []bob.Mod[*dialect.SelectQuery]) { } else { expr = append(expr, order.Asc()) } + } else { + expr = append(expr, sm.OrderBy(models.DeviceColumns.Name).Asc()) } return expr @@ -77,7 +79,7 @@ func (api *API) DevicesList(ctx context.Context, params DevicesListParams) (resu ctx, span := tracer.Start(ctx, "*API.DevicesList") defer span.End() - result.Devices, err = models.Devices.Query(ctx, api.db, params.Query()...).All() + result.Devices, err = api.GetDevices(ctx, params) if err != nil { return result, errs.Wrapw(err, "failed to query devices", "params", params) } @@ -89,3 +91,15 @@ func (api *API) DevicesList(ctx context.Context, params DevicesListParams) (resu return result, nil } + +func (api *API) GetDevices(ctx context.Context, params DevicesListParams) (result models.DeviceSlice, err error) { + ctx, span := tracer.Start(ctx, "*API.GetDevices") + defer span.End() + + result, err = models.Devices.Query(ctx, api.db, params.Query()...).All() + if err != nil { + return result, errs.Wrapw(err, "failed to query devices", "params", params) + } + + return result, nil +} diff --git a/api/subreddits_get_by_name.go b/api/subreddits_get_by_name.go index 26e1123..d2d28c6 100644 --- a/api/subreddits_get_by_name.go +++ b/api/subreddits_get_by_name.go @@ -39,6 +39,7 @@ type SubredditGetByNameImageParams struct { Sort string SFW int After time.Time + Device string } func (sgb SubredditGetByNameImageParams) IntoQuery() url.Values { @@ -62,6 +63,9 @@ func (sgb SubredditGetByNameImageParams) IntoQuery() url.Values { if !sgb.After.IsZero() { queries.Set("after", strconv.FormatInt(sgb.After.Unix(), 10)) } + if sgb.Device != "" { + queries.Set("device", sgb.Device) + } return queries } @@ -76,6 +80,7 @@ func (sgb SubredditGetByNameImageParams) IntoQueryWith(keyValue ...string) url.V func (sgb *SubredditGetByNameImageParams) FillFromQuery(query Queryable) { sgb.Q = query.Get("q") + sgb.Device = query.Get("device") sgb.Limit, _ = strconv.ParseInt(query.Get("limit"), 10, 64) if sgb.Limit < 1 { sgb.Limit = 25 @@ -119,6 +124,10 @@ func (sgb *SubredditGetByNameImageParams) CountQuery() (expr []bob.Mod[*dialect. ) } + if sgb.Device != "" { + expr = append(expr, models.SelectWhere.Images.Device.EQ(sgb.Device)) + } + if !sgb.After.IsZero() { expr = append(expr, models.SelectWhere.Images.CreatedAt.GTE(sgb.After.Unix())) } diff --git a/db/migrations/20240409222145_create_images_table.sql b/db/migrations/20240409222145_create_images_table.sql index 3886e83..aec7926 100644 --- a/db/migrations/20240409222145_create_images_table.sql +++ b/db/migrations/20240409222145_create_images_table.sql @@ -30,6 +30,7 @@ CREATE TABLE images( ); CREATE INDEX idx_subreddit_images ON images(subreddit); +CREATE INDEX idx_subreddit_device_images ON images(device, subreddit); CREATE INDEX idx_nsfw_images ON images(nsfw); CREATE INDEX idx_images_created_at_nsfw ON images(created_at DESC, nsfw); CREATE UNIQUE INDEX idx_unique_images_per_device ON images(device, post_name); diff --git a/server/routes/page_subreddits_details.go b/server/routes/page_subreddits_details.go index ad3444c..96ab840 100644 --- a/server/routes/page_subreddits_details.go +++ b/server/routes/page_subreddits_details.go @@ -1,7 +1,6 @@ package routes import ( - "fmt" "net/http" "github.com/go-chi/chi/v5" @@ -33,7 +32,6 @@ func (routes *Routes) PageSubredditsDetails(rw http.ResponseWriter, r *http.Requ code, message := errs.HTTPMessage(err) rw.WriteHeader(code) data.Error = message - fmt.Println(data) if err := detailsview.Detailsview(c, data).Render(ctx, rw); err != nil { log.New(ctx).Err(err).Error("failed to render subreddit details page") } @@ -42,6 +40,16 @@ func (routes *Routes) PageSubredditsDetails(rw http.ResponseWriter, r *http.Requ data.Subreddit = result.Subreddit data.Images = result.Images data.TotalImages = result.Total + data.Devices, err = routes.API.GetDevices(ctx, api.DevicesListParams{}) + if err != nil { + log.New(ctx).Err(err).Error("failed to get devices") + code, message := errs.HTTPMessage(err) + rw.WriteHeader(code) + data.Error = message + if err := detailsview.Detailsview(c, data).Render(ctx, rw); err != nil { + log.New(ctx).Err(err).Error("failed to render subreddit details page") + } + } if err := detailsview.Detailsview(c, data).Render(ctx, rw); err != nil { log.New(ctx).Err(err).Error("failed to render subreddit details page") diff --git a/views/subredditsview/detailsview/detailsview.templ b/views/subredditsview/detailsview/detailsview.templ index 7eaae7e..183f417 100644 --- a/views/subredditsview/detailsview/detailsview.templ +++ b/views/subredditsview/detailsview/detailsview.templ @@ -9,6 +9,7 @@ import "fmt" type Data struct { Subreddit *models.Subreddit + Devices models.DeviceSlice Images models.ImageSlice TotalImages int64 Error string @@ -54,11 +55,9 @@ templ DetailsContent(c *views.Context, data Data) {
-
- @FilterBar(c, data) - @showingImageFromTo(data) - @paginationButtons(c, data) -
+ @FilterBar(c, data) + @paginationButtons(c, data) + @showingImageFromTo(data)
for _, image := range data.Images { @components.ImageCard(image, 0) @@ -81,9 +80,9 @@ templ FilterBar(c *views.Context, data Data) { hx-target="main" hx-select="main" hx-push-url="true" - class="flex flex-wrap gap-4" + class="grid sm:grid-cols-2 md:grid-cols-3 gap-4" > -
} templ paginationButtons(_ *views.Context, data Data) { if data.TotalImages > data.Params.Limit { -
- for i, count := 1, int64(0); count < data.TotalImages; i, count = i+1, count+data.Params.Limit { - if data.Params.Offset <= count && data.Params.Offset > count-data.Params.Limit { - { strconv.Itoa(i) } - } else { - { strconv.Itoa(i) } +
+
+ for i, count := 1, int64(0); count < data.TotalImages; i, count = i+1, count+data.Params.Limit { + if data.Params.Offset <= count && data.Params.Offset > count-data.Params.Limit { + { strconv.Itoa(i) } + } else { + { strconv.Itoa(i) } + } } - } +
} } @@ -141,9 +157,17 @@ templ limitOption(params api.SubredditGetByNameImageParams, value int) { } } +templ deviceOption(params api.SubredditGetByNameImageParams, device *models.Device) { + if params.Device == device.Slug { + + } else { + + } +} + templ showingImageFromTo(data Data) { if data.TotalImages > 1 { - { showingFromToImages(data) } +

{ showingFromToImages(data) }

} }