goldberry/settings.go

169 lines
4.3 KiB
Go

package main
import (
"encoding/json"
"fmt"
"io/ioutil"
"os"
"os/user"
"path/filepath"
"strings"
)
// XXX:
// This struct is temporarily not in use while an issue with marshalling
// []ToRead in the Settings struct gets worked out. In the meantime a
// []string is being used with the string in each containing a 'magic
// string' that gets split to produce the values.
type ToRead struct {
url string `json:"ToReadURL"`
title string `json:"ToReadTitle"`
}
type VisitedPage struct {
count int
u string
}
type Settings struct {
OpenWebLinks bool
OpenGopherLinks bool
OpenFileLinks bool
KeepHistory bool
History []string
UseCustomHome bool
CustomHomeHTML string
SearchURL string
BaseFontSize int
TimeOutSeconds int
ReadingList []string
}
var settingsPath = ""
func (s Settings) FontSize() int {
return s.BaseFontSize
}
func (s *Settings) IncreaseFontSize() int {
s.BaseFontSize += 1
return s.BaseFontSize
}
func (s *Settings) DecreaseFontSize() int {
s.BaseFontSize -= 1
return s.BaseFontSize
}
func (s *Settings) AddToHistory(u string) error {
if !s.KeepHistory {
s.History = make([]string, 0)
return fmt.Errorf("No history is available")
}
if len(s.History) == 0 {
s.History = make([]string, 0, 10)
s.History = append(s.History, u)
return nil
}
s.History = append([]string{u}, s.History...)
if len(s.History) > 100 {
s.History = s.History[:101]
}
return nil
}
func (s *Settings) AddToReadingList(title, u string) (string, error) {
// FIXME: The double-tab string is being used because json.Marshall
// would not marshall the slice of ToRead structs that was being
// used prior. It resulted in empty objects in the json. Using a
// string slice with a 'magic string' for splitting is a temporary
// solution until the json.Marshall issue can be solved
stringified := u + "\t\t" + title
s.ReadingList = append(s.ReadingList, stringified)
return s.ReadingListHTML()
}
func (s Settings) ReadingListHTML() (string, error) {
var out strings.Builder
linkFormat := `<a href="%s" id="rl-%d">%s</a> <button aria-label="Remove from reading list" class="reading-list-delete" data-index="%d">&#10060;</button><br>`
out.WriteString("<h1 tabindex=\"-1\" id=\"rl-header\">Reading List</h1>\n<hr>\n")
for i, li := range s.ReadingList{
// FIXME: The double-tab string is being used because json.Marshall
// would not marshall the slice of ToRead structs that was being
// used prior. It resulted in empty objects in the json. Using a
// string slice with a 'magic string' for splitting is a temporary
// solution until the json.Marshall issue can be solved
sLn := strings.Split(li, "\t\t")
if len(sLn) < 2 {
continue
}
out.WriteString(fmt.Sprintf(linkFormat, sLn[0], i, sLn[1], i))
}
return out.String(), nil
}
func (s *Settings) RemoveFromReadingList(index int) (string, error) {
s.ReadingList = append(s.ReadingList[:index], s.ReadingList[index+1:]...)
return s.ReadingListHTML()
}
func (s Settings) GenerateConfig() {
err := os.MkdirAll(filepath.Dir(settingsPath), 0755)
if err != nil {
fmt.Fprintf(os.Stderr, "[SETTINGS] Unable to create directories for write operation")
return
}
s.Save()
}
func (s *Settings) Save() {
j, err := json.MarshalIndent(s, "", "\t")
if err != nil {
fmt.Fprintf(os.Stderr, "[SETTINGS] Unable to marshall json for write opperation")
return
}
var perms os.FileMode = 0644
fstats, err := os.Stat(settingsPath)
if err == nil {
perms = fstats.Mode()
}
f, err := os.OpenFile(settingsPath, os.O_CREATE|os.O_TRUNC|os.O_WRONLY, perms)
if err != nil {
fmt.Fprintf(os.Stderr, "[SETTINGS] Unable to open file for writing")
return
}
defer f.Close()
f.Write(j)
}
func (s *Settings) Load() {
configPath := os.Getenv("XDG_CONFIG_HOME")
if configPath == "" {
userinfo, _ := user.Current()
settingsPath = filepath.Join(userinfo.HomeDir, ".config", "goldberry", "goldberry.json")
} else {
settingsPath = filepath.Join(configPath, ".config", "goldberry.json")
}
_, err := os.Stat(settingsPath)
if err != nil {
s.GenerateConfig()
}
b, err := ioutil.ReadFile(settingsPath)
if err != nil {
return
}
json.Unmarshal(b, s)
}
func NewSettings() *Settings {
return &Settings{false, false, true, false, make([]string, 0, 10), false, "", "gemini://geminispace.info:1965/search?%s", 12, 5, make([]string, 0, 10)}
}