Files
wanderer/db/federation/like.go
2025-06-24 17:55:59 +02:00

119 lines
2.9 KiB
Go

package federation
import (
"fmt"
"os"
"path"
"pocketbase/util"
"time"
pub "github.com/go-ap/activitypub"
"github.com/pocketbase/pocketbase/core"
"github.com/pocketbase/pocketbase/tools/security"
)
// create outgoing follow activity
func CreateLikeActivity(app core.App, like *core.Record) error {
origin := os.Getenv("ORIGIN")
if origin == "" {
return fmt.Errorf("ORIGIN not set")
}
actor, err := app.FindRecordById("activitypub_actors", like.GetString("actor"))
if err != nil {
return err
}
trail, err := app.FindRecordById("trails", like.GetString("trail"))
if err != nil {
return err
}
trailAuthor, err := app.FindRecordById("activitypub_actors", trail.GetString("author"))
if err != nil {
return err
}
object := trail.GetString("iri")
if object == "" {
// trail is local
object = fmt.Sprintf("%s/api/v1/trail/%s", origin, trail.Id)
}
collection, err := app.FindCollectionByNameOrId("activitypub_activities")
if err != nil {
return err
}
recordId := security.RandomStringWithAlphabet(core.DefaultIdLength, core.DefaultIdAlphabet)
id := fmt.Sprintf("%s/api/v1/activitypub/activity/%s", origin, recordId)
activity := pub.LikeNew(pub.IRI(id), pub.IRI(object))
activity.Actor = pub.IRI(actor.GetString("iri"))
err = PostActivity(app, actor, activity, []string{trailAuthor.GetString("inbox")})
if err != nil {
return err
}
record := core.NewRecord(collection)
record.Set("id", recordId)
record.Set("iri", id)
record.Set("type", string(pub.LikeType))
record.Set("object", object)
record.Set("actor", actor.GetString("iri"))
record.Set("published", time.Now())
return app.Save(record)
}
// process incoming like activity
func ProcessLikeActivity(app core.App, actor *core.Record, activity pub.Activity) error {
origin := os.Getenv("ORIGIN")
if origin == "" {
return fmt.Errorf("ORIGIN not set")
}
trailId := path.Base(activity.Object.GetID().String())
trail, err := app.FindRecordById("trails", trailId)
if err != nil {
return err
}
trailAuthor, err := app.FindRecordById("activitypub_actors", trail.GetString("author"))
if err != nil {
return err
}
if !actor.GetBool("isLocal") {
trailLikeCollection, err := app.FindCollectionByNameOrId("trail_like")
if err != nil {
return err
}
likeRecord := core.NewRecord(trailLikeCollection)
likeRecord.Set("trail", trail.Id)
likeRecord.Set("actor", actor.Id)
err = app.Save(likeRecord)
if err != nil {
return err
}
}
// send a notification to the trail author
notification := util.Notification{
Type: util.TrailLike,
Metadata: map[string]string{
"trail_id": trail.Id,
"trail_name": trail.GetString("name"),
"trail_author": fmt.Sprintf("@%s", trailAuthor.GetString("preferred_username")),
"liker": fmt.Sprintf("@%s@%s", actor.GetString("preferred_username"), actor.GetString("domain")),
},
Seen: false,
Author: actor.Id,
}
return util.SendNotification(app, notification, trailAuthor)
}