package jsondb import ( "encoding/json" "fmt" "net/url" "os" "strings" again "git.rootprojects.org/root/go-again" ) type JSONDB struct { dburl string file *os.File json *dbjson } type dbjson struct { Schedules []again.Schedule `json:"schedules"` } func Connect(dburl string) (*JSONDB, error) { u, err := url.Parse(dburl) if nil != err { return nil, err } // json:/abspath/to/db.json fmt.Println("url.Opaque:", u.Opaque) // json:///abspath/to/db.json fmt.Println("url.Path:", u.Path) fmt.Println(u) path := u.Opaque if "" == path { path = u.Path if "" == path { // json:relpath/to/db.json // json://relpath/to/db.json path = strings.TrimSuffix(u.Host+"/"+u.Path, "/") } } f, err := os.OpenFile(path, os.O_RDWR|os.O_CREATE, 0700) if nil != err { return nil, fmt.Errorf("Couldn't open %q: %s", path, err) } stat, err := f.Stat() if 0 == stat.Size() { _, err := f.Write([]byte(`{"schedules":[]}`)) if nil != err { return nil, err } f, err = os.OpenFile(path, os.O_RDWR|os.O_CREATE, 0700) if nil != err { return nil, err } } decoder := json.NewDecoder(f) db := &dbjson{} err = decoder.Decode(db) if nil != err { return nil, fmt.Errorf("Couldn't parse %q as JSON: %s", path, err) } return &JSONDB{ dburl: dburl, file: f, json: db, }, nil } func (db *JSONDB) List() ([]again.Schedule, error) { return db.json.Schedules, nil }