summaryrefslogtreecommitdiff
diff refs
from: back
to: back
| flip
diff options
context:
space:
mode:
-rw-r--r--Dockerfile2
-rw-r--r--internal/frontmatter/parser.go1
-rw-r--r--internal/lightgallery/block.go9
-rw-r--r--internal/lightgallery/html_renderer.go3
-rw-r--r--internal/lightgallery/parser.go19
-rw-r--r--main.go31
-rw-r--r--static/input.css18
-rw-r--r--views/layouts/general-page.html4
-rw-r--r--views/pages/blog-catalogue.html36
-rw-r--r--views/pages/blog-page.html4
-rw-r--r--views/partials/catalogue-blog-cards.html14
11 files changed, 50 insertions, 91 deletions
diff --git a/Dockerfile b/Dockerfile
index 45d3e8e..e3d9e65 100644
--- a/Dockerfile
+++ b/Dockerfile
@@ -16,6 +16,4 @@ COPY --from=build-stage /builddir/views /app/views
COPY --from=build-stage /builddir/locale/*.yaml /app/locale/
COPY --from=build-stage /builddir/config/config.yaml /app/config.yaml
-RUN apk add --no-cache tzdata
-
ENTRYPOINT [ "/app/sayana-demo", "-c", "/app/config.yaml" ]
diff --git a/internal/frontmatter/parser.go b/internal/frontmatter/parser.go
index 3c00a7f..1a521c0 100644
--- a/internal/frontmatter/parser.go
+++ b/internal/frontmatter/parser.go
@@ -16,7 +16,6 @@ type Metadata struct {
Thumbnail string `yaml:"thumbnail"`
Tags []string `yaml:"tags"`
Geolocation string `yaml:"geolocation"`
- Timezone string `yaml:"timezone"`
}
func ParseFrontmatter(content []byte) (metadata *Metadata, markdown []byte, err error) {
diff --git a/internal/lightgallery/block.go b/internal/lightgallery/block.go
index 072aa3c..dade2ea 100644
--- a/internal/lightgallery/block.go
+++ b/internal/lightgallery/block.go
@@ -1,16 +1,11 @@
package lightgallery
-import (
- "time"
-
- "github.com/yuin/goldmark/ast"
-)
+import "github.com/yuin/goldmark/ast"
// LightGalleryBlock represents a light gallery block in the AST
type LightGalleryBlock struct {
ast.BaseBlock
- Images []LightGalleryImage
- Location *time.Location
+ Images []LightGalleryImage
}
type LightGalleryImage struct {
diff --git a/internal/lightgallery/html_renderer.go b/internal/lightgallery/html_renderer.go
index 77b9785..e611f0b 100644
--- a/internal/lightgallery/html_renderer.go
+++ b/internal/lightgallery/html_renderer.go
@@ -54,7 +54,6 @@ func (r *LightGalleryHTMLRenderer) renderLightGallery(w util.BufWriter, source [
imageNameParts := strings.Split(imageUrlWithoutExt, "-")
dayDate, _ := time.Parse("20060102 150405", imageNameParts[len(imageNameParts)-2]+" "+imageNameParts[len(imageNameParts)-1])
- dayDate = dayDate.In(gallery.Location)
dynamicElements = append(dynamicElements, fmt.Sprintf(`{
src:
"https://f003.backblazeb2.com/file/sayana-photos/full/%s",
@@ -71,7 +70,7 @@ func (r *LightGalleryHTMLRenderer) renderLightGallery(w util.BufWriter, source [
<p class="grow !text-[1vmax]/[0.9] text-left font-spectral text-main-dark">%s</p>
<p class="!text-[1vmax]/[0.9] text-right font-spectral text-secondary">%s</p>
</div>`+"`"+`
- }`, img.URL, img.URL, escapeHTML(img.Caption), imageUrlWithoutExt, imageUrlWithoutExt, escapeHTML(img.Caption), dayDate.Format("2006-01-02 15:04:05 -07:00")))
+ }`, img.URL, img.URL, img.Caption, imageUrlWithoutExt, imageUrlWithoutExt, img.Caption, dayDate.Format("2006-01-02 15:04:05 -07:00")))
}
w.WriteString(fmt.Sprintf(`
diff --git a/internal/lightgallery/parser.go b/internal/lightgallery/parser.go
index bd7483a..0ce209c 100644
--- a/internal/lightgallery/parser.go
+++ b/internal/lightgallery/parser.go
@@ -2,10 +2,7 @@ package lightgallery
import (
"bytes"
- "log/slog"
- "regexp"
"strings"
- "time"
"github.com/yuin/goldmark/ast"
"github.com/yuin/goldmark/parser"
@@ -25,26 +22,16 @@ func (p *LightGalleryParser) Trigger() []byte {
func (p *LightGalleryParser) Open(parent ast.Node, reader text.Reader, pc parser.Context) (ast.Node, parser.State) {
line, _ := reader.PeekLine()
- if !bytes.HasPrefix(line, []byte("{Gallery")) {
+ if !bytes.HasPrefix(line, []byte("{Gallery}")) {
return nil, parser.NoChildren
}
- r := regexp.MustCompile(`^\{Gallery:([A-Za-z0-9\+\-/]+)\}$`)
-
trimmed := bytes.TrimSpace(line)
- parts := r.FindSubmatch(trimmed)
- if len(parts) < 2 {
- slog.Warn("invalid gallery header format", slog.String("line", string(trimmed)), slog.Int("submatch_count", len(parts)))
- return nil, parser.NoChildren
- }
-
- loc, err := time.LoadLocation(string(parts[1]))
- if err != nil {
- slog.Warn("invalid location specified for a gallery", slog.String("error", err.Error()), slog.String("line", string(trimmed)), slog.String("location", string(parts[1])))
+ if !bytes.Equal(trimmed, []byte("{Gallery}")) {
return nil, parser.NoChildren
}
- return &LightGalleryBlock{Location: loc}, parser.NoChildren
+ return &LightGalleryBlock{}, parser.NoChildren
}
func (p *LightGalleryParser) Continue(node ast.Node, reader text.Reader, pc parser.Context) parser.State {
diff --git a/main.go b/main.go
index a53cc8b..7b8bfd3 100644
--- a/main.go
+++ b/main.go
@@ -121,7 +121,7 @@ func main() {
querySort := c.Query("sort")
if querySort == "" {
- querySort = "publicationDateDesc"
+ querySort = "titleAsc"
}
encodedQuery := c.Request().URI().QueryString()
@@ -146,26 +146,19 @@ func main() {
pages = []*b2.BlogPage{}
}
- tagsMap := make(map[string]int)
+ tagsSet := make(map[string]struct{})
for _, page := range pages {
- slog.Debug("enlist page for catalogue", slog.Any("page", page), slog.String("endpoint", "/"+lang+"/blog"))
+ slog.Debug("enlist page for catalogue", slog.Any("page", page), slog.String("endpoint", "/"))
for _, tag := range page.Metadata.Tags {
- tagsMap[tag]++
+ tagsSet[tag] = struct{}{}
}
}
- type Tag struct {
- Name string `json:"Name" yaml:"name"`
- Count int `json:"Count" yaml:"count"`
+ tagsArray := make([]string, 0, len(tagsSet))
+ for tag := range tagsSet {
+ tagsArray = append(tagsArray, tag)
}
-
- tagsArray := make([]Tag, 0, len(tagsMap))
- for tag, count := range tagsMap {
- tagsArray = append(tagsArray, Tag{tag, count})
- }
- slices.SortFunc(tagsArray, func(a Tag, b Tag) int {
- return strings.Compare(a.Name, b.Name)
- })
+ slices.Sort(tagsArray)
content, err := tm.Render("blog-catalogue", fiber.Map{
"QuerySort": querySort,
@@ -287,12 +280,12 @@ func main() {
case "actionDateDesc":
return strings.Compare(b["ActionDate"], a["ActionDate"])
case "publicationDateAsc":
- publishedTimeA, _ := time.Parse("2006-01-02 15:04:05 -0700", a["PublishedTime"])
- publishedTimeB, _ := time.Parse("2006-01-02 15:04:05 -0700", b["PublishedTime"])
+ publishedTimeA, _ := time.Parse(time.RFC3339, a["PublishedTime"])
+ publishedTimeB, _ := time.Parse(time.RFC3339, b["PublishedTime"])
return publishedTimeA.Compare(publishedTimeB)
case "publicationDateDesc":
- publishedTimeA, _ := time.Parse("2006-01-02 15:04:05 -0700", a["PublishedTime"])
- publishedTimeB, _ := time.Parse("2006-01-02 15:04:05 -0700", b["PublishedTime"])
+ publishedTimeA, _ := time.Parse(time.RFC3339, a["PublishedTime"])
+ publishedTimeB, _ := time.Parse(time.RFC3339, b["PublishedTime"])
return publishedTimeB.Compare(publishedTimeA)
}
return 0
diff --git a/static/input.css b/static/input.css
index aef2d8f..8776b25 100644
--- a/static/input.css
+++ b/static/input.css
@@ -154,6 +154,10 @@
background-size: calc(var(--squares-and-triangles-background-width-coef) * 1vw) calc(var(--squares-and-triangles-background-height-coef) * 1vw);
}
+body:has(.lg-container:not([class~="lg-inline"])) .desktop-sidebar-custom {
+ display: none !important;
+}
+
.mobile-topbar-custom {
width: 90vw;
height: 8%;
@@ -161,7 +165,7 @@
margin-left: 5vw;
}
-body:has(.lg-container:not([class~="lg-inline"])) #sidebar {
+body:has(.lg-container:not([class~="lg-inline"])) .mobile-topbar-custom {
display: none !important;
}
@@ -412,10 +416,6 @@ body:has(.lg-container:not([class~="lg-inline"])) #sidebar {
height: 10vh;
}
- .ar-lt-0\.8\:h-\[30vh\] {
- height: 30vh;
- }
-
.ar-lt-0\.8\:h-\[90vh\] {
height: 90vh;
}
@@ -424,10 +424,6 @@ body:has(.lg-container:not([class~="lg-inline"])) #sidebar {
width: 8vh;
}
- .ar-lt-0\.8\:w-\[80\%\] {
- width: 80%;
- }
-
.ar-lt-0\.8\:w-\[90vw\] {
width: 90vw;
}
@@ -440,10 +436,6 @@ body:has(.lg-container:not([class~="lg-inline"])) #sidebar {
max-height: 80%;
}
- .ar-lt-0\.8\:max-h-\[calc\(100\%-25vh\)\] {
- max-height: calc(100% - 25vh);
- }
-
.ar-lt-0\.8\:text-\[5vh\] {
font-size: 5vh;
}
diff --git a/views/layouts/general-page.html b/views/layouts/general-page.html
index eab7cd1..d5146f8 100644
--- a/views/layouts/general-page.html
+++ b/views/layouts/general-page.html
@@ -33,7 +33,7 @@
switchTheme(savedTheme);
</script>
- <div id="sidebar" class="bg-sidebar flex sticky flex-col ar-gt-0.8:items-center shadow-2xl z-20 w-[5vw] ar-lt-0.8:w-[90vw] ar-lt-0.4:w-[100vw] h-screen ar-lt-0.8:h-[8vh] ar-lt-0.8:ml-[5vw] ar-lt-0.4:ml-0">
+ <div class="bg-sidebar flex sticky flex-col ar-gt-0.8:items-center shadow-2xl z-20 w-[5vw] ar-lt-0.8:w-[90vw] ar-lt-0.4:w-[100vw] h-screen ar-lt-0.8:h-[8vh] ar-lt-0.8:ml-[5vw] ar-lt-0.4:ml-0">
<div class="logo-custom ar-lt-0.8:hidden text-sidebar font-patua font-extrabold text-center relative z-20">
saya.today
</div>
@@ -48,7 +48,7 @@
<div class="bg-background-dark flex z-10 ar-lt-0.8:w-[90vw] ar-lt-0.4:w-[100vw] h-screen ar-lt-0.8:ml-[5vw] ar-lt-0.4:ml-0">
<div class="pl-[0.5vw] bg-background-dark border-r-[0.4vmin] border-dashed border-main-dark"></div>
- <div class="ar-gt-0.8:min-w-fit ar-gt-0.8:max-w-[100vh] flex flex-col bg-background-dark relative pt-[1.6vmin] ml-[1.6vmin] pr-[1.6vmin]">
+ <div class="ar-gt-0.8:min-w-fit ar-gt-0.8:max-w-[100vh] flex flex-col bg-background-dark relative mt-[1.6vmin] ml-[1.6vmin] pr-[1.6vmin]">
<div class="flex flex-row mb-[0.4vmin]">
<i onclick="location.pathname += location.pathname.endsWith('/') ? '../' : '/../';" class="fas fa-circle-left hover:bg-main-dark hover:bg-opacity-10 cursor-pointer transition-colors duration-300 rounded-md text-[2vmax] mt-auto mb-auto px-[0.8vmin]"></i>
<p class="text-[2vmax] font-spectral italic font-extrabold select-none mt-auto pl-[0.8vmin] pr-[1.2vmin]">//</p>
diff --git a/views/pages/blog-catalogue.html b/views/pages/blog-catalogue.html
index 0da8d26..6fe1c82 100644
--- a/views/pages/blog-catalogue.html
+++ b/views/pages/blog-catalogue.html
@@ -1,7 +1,7 @@
{{ define "body" }}
-<div class="flex flex-row ar-lt-0.8:flex-col max-h-[calc(100%-7vmax)] ar-lt-0.8:max-h-[calc(100%-25vh)] flex-1 text-[1vmax]">
+<div class="flex flex-row ar-lt-0.8:flex-col flex-1 text-[1vmax]">
<form hx-get="/api/v1/blog-search" hx-vals='{"lang": "{{ .Lang }}"}' hx-target=".blog-cards" hx-swap="innerHTML"
- class="tags-list ar-gt-0.8:min-w-[10vh] ar-gt-0.8:max-w-[20vh] ar-gt-0.8:w-fit ar-lt-0.8:w-[100%] flex shrink-0 flex-col overflow-y-auto ar-gt-0.8:mr-[1.2vmin]">
+ class="tags-list ar-gt-0.8:min-w-[10vh] ar-gt-0.8:max-w-[20vh] ar-gt-0.8:w-fit ar-lt-0.8:w-[100%] flex shrink-0 flex-col ar-gt-0.8:mr-[1.2vmin]">
<fieldset>
<legend class="font-bold w-[100%] text-center">{{ .L.BlogSearch.TagsHeader }}</legend>
<div class="flex flex-col ar-lt-0.8:grid grid-cols-5 grid-flow-row-dense gap-[5%]">
@@ -10,7 +10,7 @@
</div>
{{- range .Tags }}
<div>
- <label><input type="checkbox" id="tag{{ .Name }}Checkbox" name="tags[]" value="{{ .Name }}" onclick="contextAll();" {{ if contains $.QueryTags .Name }}checked{{ end }}> {{ .Name }} <span class="text-secondary italic">{{ .Count }}</span></label>
+ <label><input type="checkbox" id="tag{{ . }}Checkbox" name="tags[]" value="{{ . }}" onclick="contextAll();" {{ if contains $.QueryTags . }}checked{{ end }}> {{ . }}</label>
</div>
{{- end }}
</div>
@@ -60,6 +60,20 @@
<script src="https://f003.backblazeb2.com/file/sayana-static/libs/htmx/2.0.6/htmx.min.js"></script>
<script>
+ const tagsContainers = document.querySelectorAll('form.tags-list');
+ tagsContainers.forEach(tagsContainer => {
+ const checkboxes = tagsContainer.querySelectorAll('input[type="checkbox"]');
+ anyChecked = false;
+ checkboxes.forEach(checkbox => {
+ anyChecked = checkbox.checked ? true : anyChecked;
+ });
+ if (!anyChecked) {
+ selectAll();
+ }
+ });
+</script>
+
+<script>
function selectAll() {
const tagsContainers = document.querySelectorAll('form.tags-list');
tagsContainers.forEach(tagsContainer => {
@@ -123,20 +137,4 @@
document.addEventListener('DOMContentLoaded', contextAll);
</script>
-<script>
- const tagsContainers = document.querySelectorAll('form.tags-list');
- tagsContainers.forEach(tagsContainer => {
- const checkboxes = tagsContainer.querySelectorAll('input[type="checkbox"]');
- anyChecked = false;
- checkboxes.forEach(checkbox => {
- anyChecked = checkbox.checked ? true : anyChecked;
- });
- if (!anyChecked) {
- const selectAllCheckbox = tagsContainer.querySelector('#tagsAllCheckbox');
- selectAllCheckbox.checked = true;
- selectAll();
- }
- });
-</script>
-
{{ end }}
diff --git a/views/pages/blog-page.html b/views/pages/blog-page.html
index feb63ef..5f001d6 100644
--- a/views/pages/blog-page.html
+++ b/views/pages/blog-page.html
@@ -15,11 +15,11 @@
{{ end }}
{{ define "body" }}
-<div class="bg-background-light flex flex-col grow overflow-y-auto inset-shadow p-[2.4vmin] max-h-[calc(100%-7vmax)] ar-lt-0.8:max-h-[calc(100%-25vh)]">
+<div class="bg-background-light flex flex-col grow overflow-y-auto inset-shadow p-[2.4vmin] ar-lt-0.8:max-h-[80%]">
{{ .ParsedMarkdown }}
{{- if .MapLocationX }}
<hr class="border-t-4 border-dotted border-main-dark mt-[0.8vmin] mb-[0.8vmin] w-[80%] ml-auto mr-auto">
- <div id="location-map" class="relative p-[0.8vmin] flex-none ml-auto mr-auto w-[60%] ar-lt-0.8:w-[80%] h-[40vh] ar-lt-0.8:h-[30vh]"></div>
+ <div id="location-map" class="relative p-[0.8vmin] flex-none ml-auto mr-auto w-[60%] h-[40vh]"></div>
<hr class="border-t-4 border-dotted border-main-dark mt-[0.8vmin] mb-[0.8vmin] w-[80%] ml-auto mr-auto">
{{- end }}
</div>
diff --git a/views/partials/catalogue-blog-cards.html b/views/partials/catalogue-blog-cards.html
index a9e4010..36a6184 100644
--- a/views/partials/catalogue-blog-cards.html
+++ b/views/partials/catalogue-blog-cards.html
@@ -1,15 +1,13 @@
{{- range .BlogPages }}
<hr class="first-of-type:hidden border-t-[0.3vh] my-[0.8vmin] border-dotted border-main-dark w-[80%] mx-auto">
<div class="m-[0.4vmin] flex flex-row justify-center justify-items-center">
- <img onclick="location.href='{{ .ArticleLink }}';" class="cursor-pointer object-cover rounded-[10%] select-none w-[10vmin] h-[10vmin] aspect-square my-[0.4vmin] mr-[0.8vmin]" src="https://f003.backblazeb2.com/file/sayana-photos/thumbnails/{{ .Thumbnail }}.webp">
+ <img onclick="location.href='{{ .ArticleLink }}}';" class="cursor-pointer object-cover rounded-[10%] select-none w-[10vmin] h-[10vmin] aspect-square my-[0.4vmin] mr-[0.8vmin]" src="https://f003.backblazeb2.com/file/sayana-photos/thumbnails/{{ .Thumbnail }}.webp">
<div class="grow my-[0.4vmin] mx-[0.8vmin] flex flex-col justify-center">
- <div class="flex flex-row gap-[5%] max-w-[100%]">
- <a href="{{ .ArticleLink }}" class="flex-9/12 grow-0 block text-[1vmax] cursor-pointer">
- <span class="font-extrabold">{{ .Title }}</span>
- <span class="font-extrabold select-none text-secondary">//</span>
- <span class="italic text-secondary">{{ .ActionDate }}</span>
- </a>
- <p class="flex-3/12 grow-0 text-[1vmax] italic text-secondary text-right">{{ .PublishedTime }}</p>
+ <div class="flex flex-row">
+ <a href="{{ .ArticleLink }}" class="block text-[1vmax] font-extrabold">{{ .Title }}</a>
+ <a href="{{ .ArticleLink }}" class="block text-[1vmax] font-extrabold pl-[0.4vmin] pr-[0.4vmin] select-none cursor-pointer text-secondary">//</a>
+ <a href="{{ .ArticleLink }}" class="block text-[1vmax] italic text-secondary">{{ .ActionDate }}</a>
+ <p class="text-[1vmax] italic text-secondary text-right grow">{{ .PublishedTime }}</p>
</div>
<p class="text-[1vmax] text-main-dark">{{ .ShortDescription }}</p>
<p class="text-[1vmax] text-secondary">{{ .L.TagsLabel }} {{ .Tags }}</p>