204 lines
4.4 KiB
Go
204 lines
4.4 KiB
Go
package ttbp
|
|
|
|
import (
|
|
"bufio"
|
|
"encoding/json"
|
|
"os"
|
|
"path"
|
|
"sort"
|
|
"time"
|
|
|
|
"git.tilde.town/nbsp/neofeels/config"
|
|
)
|
|
|
|
var (
|
|
PathVar = "/var/global/ttbp"
|
|
PathVarWWW = path.Join(PathVar, "www")
|
|
PathLive = "https://tilde.town/~"
|
|
PathUserFile = path.Join(PathVar, "users.txt")
|
|
PathGraff = path.Join(PathVar, "graffiti")
|
|
PathWall = path.Join(PathGraff, "wall.txt")
|
|
PathWallLock = path.Join(PathGraff, ".lock")
|
|
)
|
|
|
|
type User struct {
|
|
Name string
|
|
Publishing bool
|
|
PublishDir string
|
|
LastPublished time.Time
|
|
}
|
|
|
|
// GetUsers gets all users with a valid ttbp config, with their name, publishing
|
|
// settings, and date of last publish, if any.
|
|
func GetUsers() (users []User) {
|
|
userDirs, _ := os.ReadDir("/home")
|
|
for _, user := range userDirs {
|
|
if !user.IsDir() {
|
|
continue
|
|
}
|
|
if file, err := os.Open(path.Join("/home", user.Name(), ".ttbp/config/ttbprc")); err == nil {
|
|
defer file.Close()
|
|
|
|
// get user config
|
|
var config config.Config
|
|
decoder := json.NewDecoder(file)
|
|
err = decoder.Decode(&config)
|
|
if err != nil {
|
|
continue
|
|
}
|
|
|
|
// get last published file
|
|
entries, err := os.ReadDir(path.Join("/home", user.Name(), ".ttbp/entries"))
|
|
if err != nil {
|
|
continue
|
|
}
|
|
var lastPublished time.Time = *new(time.Time)
|
|
if len(entries) > 0 {
|
|
info, err := entries[len(entries)-1].Info()
|
|
if err != nil {
|
|
continue
|
|
}
|
|
lastPublished = info.ModTime()
|
|
}
|
|
|
|
users = append(users, User{
|
|
Name: user.Name(),
|
|
Publishing: config.Publishing,
|
|
PublishDir: config.PublishDir,
|
|
LastPublished: lastPublished,
|
|
})
|
|
}
|
|
}
|
|
return users
|
|
}
|
|
|
|
// SortUsersByRecent sorts users, putting the users with the most recent
|
|
// published feels at the beginning.
|
|
func SortUsersByRecent(users []User) []User {
|
|
sort.Slice(users, func(i, j int) bool {
|
|
return users[i].LastPublished.After(users[j].LastPublished)
|
|
})
|
|
return users
|
|
}
|
|
|
|
type Post struct {
|
|
Date time.Time
|
|
LastEdited time.Time
|
|
Words int
|
|
Author string
|
|
}
|
|
|
|
func GetPostsForUser(user string) (posts []Post) {
|
|
postFiles, err := os.ReadDir(path.Join("/home", user, ".ttbp/entries"))
|
|
if err != nil {
|
|
return
|
|
}
|
|
for _, post := range postFiles {
|
|
// retrieve date of file
|
|
// assume file ends in .txt
|
|
fileDate, err := time.Parse("20060102.txt", post.Name())
|
|
if err != nil {
|
|
continue
|
|
}
|
|
|
|
if file, err := os.Open(path.Join("/home", user, ".ttbp/entries", post.Name())); err == nil {
|
|
defer file.Close()
|
|
|
|
// get number of words in file
|
|
scanner := bufio.NewScanner(file)
|
|
scanner.Split(bufio.ScanWords)
|
|
count := 0
|
|
for scanner.Scan() {
|
|
count++
|
|
}
|
|
|
|
// get modtime of file
|
|
stat, err := file.Stat()
|
|
if err != nil {
|
|
continue
|
|
}
|
|
|
|
posts = append([]Post{Post{
|
|
Author: user,
|
|
Date: fileDate,
|
|
LastEdited: stat.ModTime(),
|
|
Words: count,
|
|
}}, posts...)
|
|
}
|
|
}
|
|
return
|
|
}
|
|
|
|
// SortUsersByRecent sorts posts, putting the posts that were most recently
|
|
// edited first in the list.
|
|
func SortPostsByRecent(posts []Post) []Post {
|
|
sort.Slice(posts, func(i, j int) bool {
|
|
return posts[i].LastEdited.After(posts[j].LastEdited)
|
|
})
|
|
return posts
|
|
}
|
|
|
|
type Subscriptions struct {
|
|
users []string
|
|
}
|
|
|
|
func GetSubscriptions() *Subscriptions {
|
|
file, err := os.OpenFile(path.Join(os.Getenv("HOME"), ".ttbp/config/subs"), os.O_RDONLY|os.O_CREATE, 0644)
|
|
if err != nil {
|
|
return &Subscriptions{}
|
|
}
|
|
defer file.Close()
|
|
|
|
var users []string
|
|
scanner := bufio.NewScanner(file)
|
|
for scanner.Scan() {
|
|
users = append(users, scanner.Text())
|
|
}
|
|
|
|
return &Subscriptions{
|
|
users: users,
|
|
}
|
|
}
|
|
|
|
func (subscriptions *Subscriptions) IsSubscribed(user User) bool {
|
|
for _, sub := range subscriptions.users {
|
|
if sub == user.Name {
|
|
return true
|
|
}
|
|
}
|
|
return false
|
|
}
|
|
|
|
func (subscriptions *Subscriptions) Subscribe(user User) {
|
|
subscriptions.users = append(subscriptions.users, user.Name)
|
|
subscriptions.write()
|
|
}
|
|
|
|
func (subscriptions *Subscriptions) Unsubscribe(user User) {
|
|
for i, sub := range subscriptions.users {
|
|
if sub == user.Name {
|
|
subscriptions.users = append(subscriptions.users[:i], subscriptions.users[i+1:]...)
|
|
subscriptions.write()
|
|
return
|
|
}
|
|
}
|
|
}
|
|
|
|
func (subscriptions *Subscriptions) write() {
|
|
file, err := os.Create(path.Join(os.Getenv("HOME"), ".ttbp/config/subs"))
|
|
if err != nil {
|
|
return
|
|
}
|
|
defer file.Close()
|
|
|
|
writer := bufio.NewWriter(file)
|
|
for _, line := range subscriptions.users {
|
|
_, err := writer.WriteString(line + "\n")
|
|
if err != nil {
|
|
return
|
|
}
|
|
}
|
|
|
|
writer.Flush()
|
|
}
|