Add comments

This commit is contained in:
JP Hastings-Spital 2023-11-12 16:48:52 +00:00
parent 50278343bc
commit 0953eb99a2
14 changed files with 193 additions and 19 deletions

View file

@ -454,4 +454,62 @@ figure {
height: 1em;
}
}
}
.interactions {
details {
summary {
cursor: pointer;
list-style: none;
&::marker, &::-webkit-details-marker {
display: none;
}
margin-bottom: 8px;
}
summary::after {
color: var(--accent);
opacity: 0.8;
content: ' (show)';
}
&[open] summary {
&::after {
content: ' (hide)';
}
}
}
ul.reactions {
margin: 0;
list-style: none;
li {
display: inline-block;
&:not(:first-of-type) {
margin: auto 0 auto 8px;
}
svg {
margin: 0;
}
}
}
ol.comments {
margin: 0;
list-style: none;
li {
margin: 1em 0;
}
.muted {
opacity: 0.6;
}
}
}

View file

@ -0,0 +1 @@
{"interactions":[{"emoji":"⭐️","url":"https://pixelfed.social/p/jphastings/619856573800023125","author":{"name":"JP","url":"https://hachyderm.io/users/byjp"},"timestamp":"0001-01-01T00:00:00Z"},{"emoji":"⭐️","url":"https://pixelfed.social/p/jphastings/619856573800023125","author":{"name":"Ben!","url":"https://pixelfed.social/bencord0"},"timestamp":"0001-01-01T00:00:00Z"},{"emoji":"⭐️","url":"https://pixelfed.social/p/jphastings/619856573800023125","author":{"name":"Thomas Zimmermann","url":"https://pixelfed.social/curlingtom"},"timestamp":"0001-01-01T00:00:00Z"},{"emoji":"⭐️","url":"https://pixelfed.social/p/jphastings/619856573800023125","author":{"name":"Ivan Jurišić","url":"https://pixelfed.social/ijurisic"},"timestamp":"0001-01-01T00:00:00Z"}],"reactions":{"⭐️":4}}

View file

@ -1 +0,0 @@
[{"emoji":"⭐️","author":{"name":"JP","url":"https://hachyderm.io/users/byjp"},"timestamp":"2022-12-14T11:16:00Z"},{"emoji":"⭐️","author":{"name":"Ben!","url":"https://pixelfed.social/bencord0"},"timestamp":"2019-09-14T08:43:33Z"},{"emoji":"⭐️","author":{"name":"Thomas Zimmermann","url":"https://pixelfed.social/curlingtom"},"timestamp":"2022-10-30T14:12:09Z"},{"emoji":"⭐️","author":{"name":"Ivan Jurišić","url":"https://pixelfed.social/ijurisic"},"timestamp":"2019-09-27T22:53:45Z"}]

View file

@ -0,0 +1 @@
{"interactions":[{"emoji":"⭐️","url":"https://pixelfed.social/p/jphastings/629220605979255535","author":{"name":"Rui Almeida","url":"https://pixelfed.social/RJCA_PT"},"timestamp":"0001-01-01T00:00:00Z"}],"reactions":{"⭐️":1}}

View file

@ -1 +0,0 @@
[{"emoji":"⭐️","author":{"name":"Rui Almeida","url":"https://pixelfed.social/RJCA_PT"},"timestamp":"2022-12-03T15:13:46Z"}]

View file

@ -0,0 +1,57 @@
{{ $interactions := index .Site.Data.interactions (split (.Path | path.Dir) "/") }}
{{ with $interactions }}
<div class="interactions">
{{ $most := 0 }}
{{ $emoji := "" }}
{{ range $thisEm, $count := .reactions }}
{{ if gt $count $most }}
{{ $most = $count }}
{{ $emoji = $thisEm }}
{{ end }}
{{ end }}
<details open>
<summary>
<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="feather feather-message-circle"><path d="M21 11.5a8.38 8.38 0 0 1-.9 3.8 8.5 8.5 0 0 1-7.6 4.7 8.38 8.38 0 0 1-3.8-.9L3 21l1.9-5.7a8.38 8.38 0 0 1-.9-3.8 8.5 8.5 0 0 1 4.7-7.6 8.38 8.38 0 0 1 3.8-.9h.5a8.48 8.48 0 0 1 8 8v.5z"></path></svg>
Reactions & comments
</summary>
<ul class="reactions">
{{ range $thisEm, $count := .reactions }}
{{ if gt $count 0 }}
<li>
{{ if eq $thisEm "❤️" }}<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="lch(55% 71 27)" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="feather feather-heart"><path d="M20.84 4.61a5.5 5.5 0 0 0-7.78 0L12 5.67l-1.06-1.06a5.5 5.5 0 0 0-7.78 7.78l1.06 1.06L12 21.23l7.78-7.78 1.06-1.06a5.5 5.5 0 0 0 0-7.78z"></path></svg>{{ end }}
{{ if eq $thisEm "⭐️" }}<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="lch(65% 71 81)" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="feather feather-star"><polygon points="12 2 15.09 8.26 22 9.27 17 14.14 18.18 21.02 12 17.77 5.82 21.02 7 14.14 2 9.27 8.91 8.26 12 2"></polygon></svg>{{ end }}
{{ if eq $thisEm "👍" }}<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="lch(55% 71 270)" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="feather feather-thumbs-up"><path d="M14 9V5a3 3 0 0 0-3-3l-4 9v11h11.28a2 2 0 0 0 2-1.7l1.38-9a2 2 0 0 0-2-2.3zM7 22H4a2 2 0 0 1-2-2v-7a2 2 0 0 1 2-2h3"></path></svg>{{ end }}
{{ if eq $thisEm "🔁" }}<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="lch(55% 71 130)" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="feather feather-repeat"><polyline points="17 1 21 5 17 9"></polyline><path d="M3 11V9a4 4 0 0 1 4-4h14"></path><polyline points="7 23 3 19 7 15"></polyline><path d="M21 13v2a4 4 0 0 1-4 4H3"></path></svg>{{ end }}
{{ if eq $thisEm "💬" }}<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="lch(65% 0 0)" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="feather feather-message-circle"><path d="M21 11.5a8.38 8.38 0 0 1-.9 3.8 8.5 8.5 0 0 1-7.6 4.7 8.38 8.38 0 0 1-3.8-.9L3 21l1.9-5.7a8.38 8.38 0 0 1-.9-3.8 8.5 8.5 0 0 1 4.7-7.6 8.38 8.38 0 0 1 3.8-.9h.5a8.48 8.48 0 0 1 8 8v.5z"></path></svg>{{ end }}
{{ $count }}
</li>
{{ end }}
{{ end }}
</ul>
<ol class="comments">
{{ range .interactions }}
{{ if not .comment }}
{{ continue }}
{{ end }}
<li>
<a href="{{.author.url}}">{{ .author.name }}</a>: {{ .comment }}
<span class="muted">(<a href="{{.url }}">{{- partial "rel-date.html" (dict "time" .timestamp "rel" $.Page.Date) -}}</a>)</span>
</li>
{{ end }}
</ol>
</details>
</div>
{{ else }}
<p>
<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round" class="feather feather-message-circle"><path d="M21 11.5a8.38 8.38 0 0 1-.9 3.8 8.5 8.5 0 0 1-7.6 4.7 8.38 8.38 0 0 1-3.8-.9L3 21l1.9-5.7a8.38 8.38 0 0 1-.9-3.8 8.5 8.5 0 0 1 4.7-7.6 8.38 8.38 0 0 1 3.8-.9h.5a8.48 8.48 0 0 1 8 8v.5z"></path></svg>
No comments or reactions
</p>
{{ end }}

View file

@ -0,0 +1,14 @@
{{- $desc := "0s" -}}
{{- $diff := (time .time).Sub (time .rel) -}}
{{- if gt $diff.Hours 168 -}}
{{- $desc = printf "%.0fw" (div $diff.Hours 168) -}}
{{- else if gt $diff.Hours 24 -}}
{{- $desc = printf "%.0fd" (div $diff.Hours 24) -}}
{{- else if gt $diff.Minutes 60 -}}
{{- $desc = printf "%.0fh" (div $diff.Minutes 60) -}}
{{- else if gt $diff.Seconds 60 -}}
{{- $desc = printf "%.0fm" (div $diff.Seconds 60) -}}
{{- else -}}
{{- $desc = printf "%.0fs" (div $diff.Seconds 1) -}}
{{- end -}}
<time timestamp="{{ .time }}" title="{{ time .time | dateFormat "2006-01-02 03:04 MST" }}">{{- $desc -}}</time>

View file

@ -41,6 +41,8 @@
{{ dateFormat .Site.Params.dateformNumTime .Date }}
</date>
</p>
{{ partial "interactions.html" . }}
</div>
<hr />

View file

@ -53,17 +53,31 @@ func (b *backfeeder) BackfeedAll(toBackfeed ToBackfeedList) error {
}
func writeInteractions(dir string, ias []shared.Interaction) error {
if err := os.MkdirAll(dir, 0755); err != nil {
if err := os.MkdirAll(filepath.Dir(dir), 0755); err != nil {
return err
}
path := filepath.Join(dir, "interactions.json")
path := dir + ".json"
f, err := os.OpenFile(path, os.O_CREATE|os.O_WRONLY|os.O_TRUNC, 0644)
if err != nil {
return err
}
defer f.Close()
enc := json.NewEncoder(f)
return enc.Encode(ias)
split := map[string]interface{}{
"interactions": ias,
"reactions": make(map[string]int),
}
for _, ia := range ias {
if ia.Emoji != "" {
split["reactions"].(map[string]int)[ia.Emoji]++
}
if ia.Comment != "" {
split["reactions"].(map[string]int)["💬"]++
}
}
return enc.Encode(split)
}

View file

@ -37,6 +37,8 @@ type config struct {
syndicationMatchers map[string]*regexp.Regexp
urlToPublicPath func(string) string
urlToInteractionsPath func(string) string
performBackfeed bool
}
func parseConfig(cfgPath string) (*config, error) {
@ -50,12 +52,16 @@ func parseConfig(cfgPath string) (*config, error) {
feeds: []string{},
services: services.New(),
syndicationMatchers: make(map[string]*regexp.Regexp),
performBackfeed: cfgData.InteractionsDir != "",
urlToPublicPath: func(url string) string {
return path.Join(cfgData.PublishRoot, strings.TrimPrefix(url, cfgData.PublishURL))
},
urlToInteractionsPath: func(url string) string {
}
if cfg.performBackfeed {
cfg.urlToInteractionsPath = func(url string) string {
return path.Join(cfgData.InteractionsDir, strings.TrimPrefix(url, cfgData.PublishURL))
},
}
}
cfg.content, err = doublestar.Glob(os.DirFS("."), cfgData.ContentGlob)
@ -80,11 +86,14 @@ func parseConfig(cfgPath string) (*config, error) {
return nil, err
}
bf, err := svc.BackfeedMatcher()
if err != nil {
return nil, fmt.Errorf("cannot perform backfeed matching for '%s' because %w", name, err)
if cfg.performBackfeed {
bf, err := svc.BackfeedMatcher()
if err != nil {
return nil, fmt.Errorf("cannot perform backfeed matching for '%s' because %w", name, err)
}
cfg.syndicationMatchers[name] = bf
}
cfg.syndicationMatchers[name] = bf
serviceTags = append(serviceTags, name)
}
cfg.tagMatcher, err = shared.TagMatcher(serviceTags)

View file

@ -34,7 +34,7 @@ func main() {
check(err)
if len(services) > 0 {
fmt.Fprintf(os.Stderr, "Connecting to %s to syndicate & backfeed…\n", strings.Join(services, ", "))
fmt.Fprintf(os.Stderr, "Connecting to %s to syndicate…\n", strings.Join(services, ", "))
for _, sname := range services {
if err := cfg.services.Init(sname); err != nil {
check(fmt.Errorf("couldn't connect to %s: %w", sname, err))
@ -53,6 +53,10 @@ func main() {
}
}
if !cfg.performBackfeed {
continue
}
fmt.Fprintf(os.Stderr, "Found %d existing syndications to backfeed from %s\n", len(toBackfeed), feed)
if err := bkfd.BackfeedAll(toBackfeed); err != nil {
fmt.Fprintf(os.Stderr, "Couldn't backfeed syndications: %v\n", err)

View file

@ -1,7 +1,23 @@
package instagram
import "github.com/by-jp/www.byjp.me/tools/syndicate/shared"
import (
"fmt"
"github.com/by-jp/www.byjp.me/tools/syndicate/shared"
)
func (s *service) Interactions(url string) ([]shared.Interaction, error) {
return nil, nil
u, err := s.insta.Profiles.ByName(s.username)
if err != nil {
return nil, fmt.Errorf("unable to load your feed to scan for interactions: %w", err)
}
feed := u.Feed()
fmt.Println(feed, feed.Items, feed.NumResults, feed.Status)
if err := feed.GetCommentInfo(); err != nil {
return nil, fmt.Errorf("unable load feed comment info: %w", err)
}
return nil, fmt.Errorf("not implemented")
}

View file

@ -25,12 +25,12 @@ func (s *service) Interactions(url string) ([]shared.Interaction, error) {
for _, acc := range favs {
ias = append(ias, shared.Interaction{
Emoji: "⭐️",
URL: url,
Author: shared.Author{
Name: acc.DisplayName,
URL: acc.URL,
AvatarURL: acc.Avatar,
},
Timestamp: acc.CreatedAt,
})
}
@ -42,12 +42,12 @@ func (s *service) Interactions(url string) ([]shared.Interaction, error) {
for _, acc := range reblogs {
ias = append(ias, shared.Interaction{
Emoji: "🔁",
URL: url,
Author: shared.Author{
Name: acc.DisplayName,
URL: acc.URL,
AvatarURL: acc.Avatar,
},
Timestamp: acc.CreatedAt,
})
}

View file

@ -28,12 +28,12 @@ type Interaction struct {
// eg. Repost is 🔁, Facebook is 👍, Instagram is ♥️, Mastodon is ⭐️, Medium is 👏
Emoji string `json:"emoji,omitempty"`
// The URL of the original interaction
URL string `json:"url,omitempty"`
URL string `json:"url"`
// If there's a comment associated with the interaction
Comment string `json:"comment,omitempty"`
// Details of the author
Author Author `json:"author"`
Timestamp time.Time `json:"timestamp"`
Timestamp time.Time `json:"timestamp,omitempty"`
}
type Author struct {