Section option to show full post content on index & fixes

This commit is contained in:
Jan-Lukas Else 2021-07-31 13:20:51 +02:00
parent fcf299d1a1
commit 5dafac827c
14 changed files with 145 additions and 110 deletions

View File

@ -80,6 +80,7 @@ type configSection struct {
Title string `mapstructure:"title"`
Description string `mapstructure:"description"`
PathTemplate string `mapstructure:"pathtemplate"`
ShowFull bool `mapstructure:"showFull"`
}
type configTaxonomy struct {
@ -99,7 +100,6 @@ type configMenuItem struct {
type configPhotos struct {
Enabled bool `mapstructure:"enabled"`
Parameter string `mapstructure:"parameter"`
Path string `mapstructure:"path"`
Title string `mapstructure:"title"`
Description string `mapstructure:"description"`
@ -197,7 +197,9 @@ type configHooks struct {
type configMicropub struct {
CategoryParam string `mapstructure:"categoryParam"`
ReplyParam string `mapstructure:"replyParam"`
ReplyTitleParam string `mapstructure:"replyTitleParam"`
LikeParam string `mapstructure:"likeParam"`
LikeTitleParam string `mapstructure:"likeTitleParam"`
BookmarkParam string `mapstructure:"bookmarkParam"`
AudioParam string `mapstructure:"audioParam"`
PhotoParam string `mapstructure:"photoParam"`
@ -281,7 +283,9 @@ func (a *goBlog) initConfig() error {
viper.SetDefault("hooks.shell", "/bin/bash")
viper.SetDefault("micropub.categoryParam", "tags")
viper.SetDefault("micropub.replyParam", "replylink")
viper.SetDefault("micropub.replyTitleParam", "replytitle")
viper.SetDefault("micropub.likeParam", "likelink")
viper.SetDefault("micropub.likeTitleParam", "liketitle")
viper.SetDefault("micropub.bookmarkParam", "link")
viper.SetDefault("micropub.audioParam", "audio")
viper.SetDefault("micropub.photoParam", "images")

View File

@ -98,11 +98,14 @@ micropub:
# You can set parameters via the UI of your MicroPub editor or via front matter in the content
categoryParam: tags
replyParam: replylink
replyTitleParam: replytitle
likeParam: likelink
likeTitleParam: liketitle
bookmarkParam: link
audioParam: audio
photoParam: images
photoDescriptionParam: imagealts
locationParam: location
# Notifications
notifications:
@ -142,6 +145,7 @@ blogs:
title: Micro
description: "You can also use **Markdown** here." # Section description, can also use Markdown
pathtemplate: "{{printf \"/%v/%02d/%02d/%v\" .Section .Year .Month .Slug}}"
showFull: true # Show full post content instead of just the summary on index pages
# Taxonomies
taxonomies:
- name: tags # Code of taxonomy (used via post parameters)
@ -166,7 +170,6 @@ blogs:
# Index page which shows all posts with photos
photos:
enabled: true # Enable
parameter: images # Parameter which includes photo links
path: /photos # (Optional) Set a custom path (relative to blog path)
title: Photos # Title
description: Instead of using Instagram, I prefer uploading pictures to my blog. # Description

2
geo.go
View File

@ -12,8 +12,6 @@ import (
"github.com/thoas/go-funk"
)
const geoParam = "location"
func (a *goBlog) geoTitle(g *gogeouri.Geo, lang string) string {
if name, ok := g.Parameters["name"]; ok && len(name) > 0 && name[0] != "" {
return name[0]

View File

@ -23,8 +23,8 @@ func (a *goBlog) serveGeoMap(w http.ResponseWriter, r *http.Request) {
allPostsWithLocation, err := a.db.getPosts(&postsRequestConfig{
blog: blog,
status: statusPublished,
parameter: geoParam,
withOnlyParameters: []string{geoParam},
parameter: a.cfg.Micropub.LocationParam,
withOnlyParameters: []string{a.cfg.Micropub.LocationParam},
})
if err != nil {
a.serveError(w, r, err.Error(), http.StatusInternalServerError)
@ -49,7 +49,7 @@ func (a *goBlog) serveGeoMap(w http.ResponseWriter, r *http.Request) {
var locations []*templateLocation
for _, p := range allPostsWithLocation {
if g := p.GeoURI(); g != nil {
if g := a.geoURI(p); g != nil {
locations = append(locations, &templateLocation{
Lat: g.Latitude,
Lon: g.Longitude,

View File

@ -237,7 +237,7 @@ func (a *goBlog) blogPhotosRouter(conf *configBlog) func(r chi.Router) {
a.cacheMiddleware,
middleware.WithValue(indexConfigKey, &indexConfig{
path: photoPath,
parameter: pc.Parameter,
parameter: a.cfg.Micropub.PhotoParam,
title: pc.Title,
description: pc.Description,
summaryTemplate: templatePhotosSummary,

View File

@ -7,12 +7,12 @@ import (
"mime"
"net/http"
"net/url"
"reflect"
"regexp"
"strconv"
"strings"
"github.com/spf13/cast"
"github.com/thoas/go-funk"
"go.goblog.app/app/pkgs/contenttype"
"gopkg.in/yaml.v3"
)
@ -547,11 +547,7 @@ func (a *goBlog) micropubUpdateAdd(p *post, add map[string][]interface{}) {
case "updated":
p.Updated = strings.TrimSpace(strings.Join(cast.ToStringSlice(value), " "))
case "category":
category := p.Parameters[a.cfg.Micropub.CategoryParam]
if category == nil {
category = []string{}
}
p.Parameters[a.cfg.Micropub.CategoryParam] = append(category, cast.ToStringSlice(value)...)
p.Parameters[a.cfg.Micropub.CategoryParam] = append(p.Parameters[a.cfg.Micropub.CategoryParam], cast.ToStringSlice(value)...)
case "in-reply-to":
p.Parameters[a.cfg.Micropub.ReplyParam] = cast.ToStringSlice(value)
case "like-of":
@ -559,67 +555,74 @@ func (a *goBlog) micropubUpdateAdd(p *post, add map[string][]interface{}) {
case "bookmark-of":
p.Parameters[a.cfg.Micropub.BookmarkParam] = cast.ToStringSlice(value)
case "audio":
audio := p.Parameters[a.cfg.Micropub.CategoryParam]
if audio == nil {
audio = []string{}
}
p.Parameters[a.cfg.Micropub.AudioParam] = append(audio, cast.ToStringSlice(value)...)
p.Parameters[a.cfg.Micropub.AudioParam] = append(p.Parameters[a.cfg.Micropub.AudioParam], cast.ToStringSlice(value)...)
// TODO: photo
}
}
}
func (a *goBlog) micropubUpdateDelete(p *post, del interface{}) {
if del != nil {
if reflect.TypeOf(del).Kind() == reflect.Slice {
toDelete, ok := del.([]interface{})
if ok {
for _, key := range toDelete {
switch key {
case "content":
p.Content = ""
case "published":
p.Published = ""
case "updated":
p.Updated = ""
case "category":
delete(p.Parameters, a.cfg.Micropub.CategoryParam)
case "in-reply-to":
delete(p.Parameters, a.cfg.Micropub.ReplyParam)
case "like-of":
delete(p.Parameters, a.cfg.Micropub.LikeParam)
case "bookmark-of":
delete(p.Parameters, a.cfg.Micropub.BookmarkParam)
case "audio":
delete(p.Parameters, a.cfg.Micropub.AudioParam)
case "photo":
delete(p.Parameters, a.cfg.Micropub.PhotoParam)
delete(p.Parameters, a.cfg.Micropub.PhotoDescriptionParam)
}
}
if del == nil {
return
}
deleteProperties, ok := del.([]interface{})
if ok {
// Completely remove properties
for _, prop := range deleteProperties {
switch prop {
case "content":
p.Content = ""
case "published":
p.Published = ""
case "updated":
p.Updated = ""
case "category":
delete(p.Parameters, a.cfg.Micropub.CategoryParam)
case "in-reply-to":
delete(p.Parameters, a.cfg.Micropub.ReplyParam)
delete(p.Parameters, a.cfg.Micropub.ReplyTitleParam)
case "like-of":
delete(p.Parameters, a.cfg.Micropub.LikeParam)
delete(p.Parameters, a.cfg.Micropub.LikeTitleParam)
case "bookmark-of":
delete(p.Parameters, a.cfg.Micropub.BookmarkParam)
case "audio":
delete(p.Parameters, a.cfg.Micropub.AudioParam)
case "photo":
delete(p.Parameters, a.cfg.Micropub.PhotoParam)
delete(p.Parameters, a.cfg.Micropub.PhotoDescriptionParam)
}
} else {
toDelete, ok := del.(map[string]interface{})
if ok {
for key := range toDelete {
if ok {
switch key {
case "content":
p.Content = ""
case "published":
p.Published = ""
case "updated":
p.Updated = ""
case "in-reply-to":
delete(p.Parameters, a.cfg.Micropub.ReplyParam)
case "like-of":
delete(p.Parameters, a.cfg.Micropub.LikeParam)
case "bookmark-of":
delete(p.Parameters, a.cfg.Micropub.BookmarkParam)
// Use content to edit other parameters
}
}
}
}
// Return
return
}
toDelete, ok := del.(map[string]interface{})
if ok {
// Only delete parts of properties
for key, values := range toDelete {
switch key {
// Properties to completely delete
case "content":
p.Content = ""
case "published":
p.Published = ""
case "updated":
p.Updated = ""
case "in-reply-to":
delete(p.Parameters, a.cfg.Micropub.ReplyParam)
delete(p.Parameters, a.cfg.Micropub.ReplyTitleParam)
case "like-of":
delete(p.Parameters, a.cfg.Micropub.LikeParam)
delete(p.Parameters, a.cfg.Micropub.LikeTitleParam)
case "bookmark-of":
delete(p.Parameters, a.cfg.Micropub.BookmarkParam)
// Properties to delete part of
// TODO: Support partial deletes of more properties
case "category":
delValues := cast.ToStringSlice(values)
p.Parameters[a.cfg.Micropub.CategoryParam] = funk.FilterString(p.Parameters[a.cfg.Micropub.CategoryParam], func(s string) bool {
return !funk.ContainsString(delValues, s)
})
}
}
}

View File

@ -32,10 +32,6 @@ func postParameter(p *post, parameter string) []string {
return p.Parameters[parameter]
}
func postHasParameter(p *post, parameter string) bool {
return len(p.Parameters[parameter]) > 0
}
func (p *post) firstParameter(parameter string) (result string) {
if pp := p.Parameters[parameter]; len(pp) > 0 {
result = pp[0]
@ -43,10 +39,6 @@ func (p *post) firstParameter(parameter string) (result string) {
return
}
func firstPostParameter(p *post, parameter string) string {
return p.firstParameter(parameter)
}
func (a *goBlog) postHtml(p *post, absolute bool) template.HTML {
p.renderMutex.RLock()
// Check cache
@ -61,7 +53,7 @@ func (a *goBlog) postHtml(p *post, absolute bool) template.HTML {
// Build HTML
var htmlBuilder strings.Builder
// Add audio to the top
if audio, ok := p.Parameters["audio"]; ok && len(audio) > 0 {
if audio, ok := p.Parameters[a.cfg.Micropub.AudioParam]; ok && len(audio) > 0 {
for _, a := range audio {
htmlBuilder.WriteString(`<audio controls preload=none><source src="`)
htmlBuilder.WriteString(a)
@ -75,8 +67,8 @@ func (a *goBlog) postHtml(p *post, absolute bool) template.HTML {
return ""
}
htmlBuilder.Write(htmlContent)
// Add links to the bottom
if link, ok := p.Parameters["link"]; ok && len(link) > 0 {
// Add bookmark links to the bottom
if link, ok := p.Parameters[a.cfg.Micropub.BookmarkParam]; ok && len(link) > 0 {
for _, l := range link {
htmlBuilder.WriteString(`<p><a class=u-bookmark-of href="`)
htmlBuilder.WriteString(l)
@ -193,14 +185,16 @@ func (a *goBlog) postToMfItem(p *post) *microformatItem {
}
}
// Public because of rendering
func (p *post) Title() string {
return p.firstParameter("title")
func (a *goBlog) showFull(p *post) bool {
if p.Section == "" {
return false
}
sec, ok := a.cfg.Blogs[p.Blog].Sections[p.Section]
return ok && sec != nil && sec.ShowFull
}
func (p *post) GeoURI() *gogeouri.Geo {
loc := p.firstParameter("location")
func (a *goBlog) geoURI(p *post) *gogeouri.Geo {
loc := p.firstParameter(a.cfg.Micropub.LocationParam)
if loc == "" {
return nil
}
@ -208,6 +202,32 @@ func (p *post) GeoURI() *gogeouri.Geo {
return g
}
func (a *goBlog) replyLink(p *post) string {
return p.firstParameter(a.cfg.Micropub.ReplyParam)
}
func (a *goBlog) replyTitle(p *post) string {
return p.firstParameter(a.cfg.Micropub.ReplyTitleParam)
}
func (a *goBlog) likeLink(p *post) string {
return p.firstParameter(a.cfg.Micropub.LikeParam)
}
func (a *goBlog) likeTitle(p *post) string {
return p.firstParameter(a.cfg.Micropub.LikeTitleParam)
}
func (a *goBlog) photoLinks(p *post) []string {
return p.Parameters[a.cfg.Micropub.PhotoParam]
}
// Public because of rendering
func (p *post) Title() string {
return p.firstParameter("title")
}
func (p *post) Old() bool {
pub := p.Published
if pub == "" {

View File

@ -48,13 +48,18 @@ func (a *goBlog) initRendering() error {
"md": a.safeRenderMarkdownAsHTML,
"html": wrapStringAsHTML,
// Post specific
"p": firstPostParameter,
"ps": postParameter,
"hasp": postHasParameter,
"content": a.postHtml,
"summary": a.postSummary,
"translations": a.postTranslations,
"shorturl": a.shortPostURL,
"showfull": a.showFull,
"geouri": a.geoURI,
"replylink": a.replyLink,
"replytitle": a.replyTitle,
"likelink": a.likeLink,
"liketitle": a.likeTitle,
"photolinks": a.photoLinks,
// Others
"dateformat": dateFormat,
"isodate": isoDateFormat,

View File

@ -1,18 +1,18 @@
{{ define "photosummary" }}
<article class="h-entry border-bottom">
{{ if gt .Data.Priority 0 }}<p>📌 {{ string .Blog.Lang "pinned" }}</p>{{ end }}
{{ if p .Data "title" }}
{{ if .Data.Title }}
<h2 class="p-name">
<a class="u-url" href="{{ .Data.Path }}">
{{ p .Data "title" }}
{{ .Data.Title }}
</a>
</h2>
{{ end }}
{{ include "summarymeta" . }}
{{ range $i, $photo := ( ps .Data .Blog.Photos.Parameter ) }}
{{ range $i, $photo := (photolinks .Data) }}
{{ md ( printf "![](%s)" $photo ) }}
{{ end }}
<p class="p-summary">{{ summary .Data }}</p>
<p>{{ if (hasp .Data "images") }}🖼️ {{ end }}<a class="u-url" href="{{ .Data.Path }}">{{ string .Blog.Lang "view" }}</a></p>
<p>{{ if (photolinks .Data) }}🖼️ {{ end }}<a class="u-url" href="{{ .Data.Path }}">{{ string .Blog.Lang "view" }}</a></p>
</article>
{{ end }}

View File

@ -19,7 +19,7 @@
{{ with .Data.Updated }}
<meta itemprop="dateModified" content="{{ dateformat . $ISO8601 }}">
{{ end }}
{{ range $key, $image := ps .Data "images" }}
{{ range $key, $image := photolinks .Data }}
<meta itemprop="image" content="{{ $image }}">
<meta property="og:image" content="{{ $image }}">
<meta property="twitter:image" content="{{ $image }}">

View File

@ -1,15 +1,6 @@
{{ define "postmeta" }}
<div class="p">
{{ include "summaryandpostmeta" . }}
{{ $bloglang := .Blog.Lang }}
{{ $geo := .Data.GeoURI }}
{{ if $geo }}
<div>📍 <a class="p-location h-geo" href="{{ geolink $geo }}" target="_blank" rel="nofollow noopener noreferrer">
<span class="p-name">{{ geotitle $geo .Blog.Lang }}</span>
<data class="p-longitude" value="{{ $geo.Longitude }}" />
<data class="p-latitude" value="{{ $geo.Latitude }}" />
</a></div>
{{ end }}
{{ $translations := (translations .Data) }}
{{ if gt (len $translations) 0 }}
<div>{{ string .Blog.Lang "translations" }}: {{ $delimiter := "" }}{{ range $i, $t := $translations }}{{ $delimiter }}<a href="{{ $t.Path }}" translate="no">{{ $t.Title }}</a>{{ $delimiter = ", " }}{{ end }}</div>

View File

@ -1,15 +1,19 @@
{{ define "summary" }}
<article class="h-entry border-bottom">
{{ if gt .Data.Priority 0 }}<p>📌 {{ string .Blog.Lang "pinned" }}</p>{{ end }}
{{ if p .Data "title" }}
{{ if .Data.Title }}
<h2 class="p-name">
<a class="u-url" href="{{ .Data.Path }}">
{{ p .Data "title" }}
{{ .Data.Title }}
</a>
</h2>
{{ end }}
{{ include "summarymeta" . }}
<p class="p-summary">{{ summary .Data }}</p>
<p>{{ if (hasp .Data "images") }}🖼️ {{ end }}<a class="u-url" href="{{ .Data.Path }}">{{ string .Blog.Lang "view" }}</a></p>
{{ if showfull .Data }}
<div class=e-content>{{ content .Data false }}</div>
{{ else }}
<p class=p-summary>{{ summary .Data }}</p>
{{ end }}
<p>{{ if (photolinks .Data) }}🖼️ {{ end }}<a class="u-url" href="{{ .Data.Path }}">{{ string .Blog.Lang "view" }}</a></p>
</article>
{{ end }}

View File

@ -2,10 +2,18 @@
{{ $section := (index .Blog.Sections .Data.Section) }}
{{ if .Data.Published }}<div>{{ string .Blog.Lang "publishedon" }} <time class="dt-published" datetime="{{ dateformat .Data.Published "2006-01-02T15:04:05Z07:00"}}">{{ isodate .Data.Published }}</time>{{ if $section }} in <a href="{{ .Blog.RelativePath $section.Name }}">{{ $section.Title }}</a>{{ end }}</div>{{ end }}
{{ if .Data.Updated }}<div>{{ string .Blog.Lang "updatedon" }} <time class="dt-updated" datetime="{{ dateformat .Data.Updated "2006-01-02T15:04:05Z07:00"}}">{{ isodate .Data.Updated }}</time></div>{{ end }}
{{ if p .Data "replylink" }}
<div>{{ string .Blog.Lang "replyto" }}: <a class="u-in-reply-to" href="{{ p .Data "replylink" }}" target="_blank" rel="noopener">{{ with (p .Data "replytitle") }}{{ . }}{{ else }}{{ p .Data "replylink" }}{{ end }}</a></div>
{{ if replylink .Data }}
<div>{{ string .Blog.Lang "replyto" }}: <a class="u-in-reply-to" href="{{ replylink .Data }}" target="_blank" rel="noopener">{{ with (replytitle .Data) }}{{ . }}{{ else }}{{ replylink .Data }}{{ end }}</a></div>
{{ end }}
{{ if p .Data "likelink" }}
<div>{{ string .Blog.Lang "likeof" }}: <a class="u-like-of" href="{{ p .Data "likelink" }}" target="_blank" rel="noopener">{{ with (p .Data "liketitle") }}{{ . }}{{ else }}{{ p .Data "likelink" }}{{ end }}</a></div>
{{ if likelink .Data }}
<div>{{ string .Blog.Lang "likeof" }}: <a class="u-like-of" href="{{ likelink .Data }}" target="_blank" rel="noopener">{{ with (liketitle .Data) }}{{ . }}{{ else }}{{ likelink .Data }}{{ end }}</a></div>
{{ end }}
{{ $geo := geouri .Data }}
{{ if $geo }}
<div>📍 <a class="p-location h-geo" href="{{ geolink $geo }}" target="_blank" rel="nofollow noopener noreferrer">
<span class="p-name">{{ geotitle $geo .Blog.Lang }}</span>
<data class="p-longitude" value="{{ $geo.Longitude }}" />
<data class="p-latitude" value="{{ $geo.Latitude }}" />
</a></div>
{{ end }}
{{ end }}

View File

@ -35,7 +35,6 @@ func (a *goBlog) sendWebmentions(p *post) error {
return err
}
links = append(links, contentLinks...)
links = append(links, p.firstParameter("link"))
if mpc := a.cfg.Micropub; mpc != nil {
links = append(links, p.firstParameter(a.cfg.Micropub.LikeParam), p.firstParameter(a.cfg.Micropub.ReplyParam), p.firstParameter(a.cfg.Micropub.BookmarkParam))
}