feat(dir2config): defaults
This commit is contained in:
143
pkg/clustersconfig/defaults.go
Normal file
143
pkg/clustersconfig/defaults.go
Normal file
@ -0,0 +1,143 @@
|
||||
package clustersconfig
|
||||
|
||||
import (
|
||||
"fmt"
|
||||
"io"
|
||||
"io/ioutil"
|
||||
"log"
|
||||
"path"
|
||||
"strings"
|
||||
|
||||
billy "gopkg.in/src-d/go-billy.v4"
|
||||
git "gopkg.in/src-d/go-git.v4"
|
||||
"gopkg.in/src-d/go-git.v4/plumbing"
|
||||
"gopkg.in/src-d/go-git.v4/plumbing/object"
|
||||
yaml "gopkg.in/yaml.v2"
|
||||
)
|
||||
|
||||
type Defaults struct {
|
||||
repo *git.Repository
|
||||
fs billy.Filesystem
|
||||
}
|
||||
|
||||
type defaultRef struct {
|
||||
From string
|
||||
}
|
||||
|
||||
func NewDefaults(path string) (d *Defaults, err error) {
|
||||
repo, err := git.PlainOpen(path)
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
d = &Defaults{
|
||||
repo: repo,
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
func (d *Defaults) Load(dir, suffix string, value Rev, data []byte) (err error) {
|
||||
ref := defaultRef{}
|
||||
|
||||
if err = yaml.Unmarshal(data, &ref); err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
if len(ref.From) != 0 {
|
||||
if Debug {
|
||||
log.Printf("loading defaults %q", ref.From)
|
||||
}
|
||||
|
||||
parts := strings.SplitN(ref.From, ":", 2)
|
||||
if len(parts) != 2 {
|
||||
err = fmt.Errorf("bad default reference: %q", ref.From)
|
||||
return
|
||||
}
|
||||
rev, fileName := parts[0], parts[1]
|
||||
|
||||
if err = d.decodeDefault(rev, path.Join(dir, fileName+suffix), value); err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
value.SetRev(rev)
|
||||
}
|
||||
|
||||
err = yaml.Unmarshal(data, value)
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
func (d *Defaults) Open(rev, filePath string) (rd io.Reader, err error) {
|
||||
tree, err := d.treeAt(rev)
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
file, err := tree.File(filePath)
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
return file.Reader()
|
||||
}
|
||||
|
||||
func (d *Defaults) ReadAll(rev, filePath string) (ba []byte, err error) {
|
||||
rd, err := d.Open(rev, filePath)
|
||||
return ioutil.ReadAll(rd)
|
||||
}
|
||||
|
||||
func (d *Defaults) List(rev, dir string) (names []string, err error) {
|
||||
tree, err := d.treeAt(rev)
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
err = tree.Files().ForEach(func(f *object.File) (err error) {
|
||||
if !strings.HasSuffix(f.Name, ".yaml") {
|
||||
return
|
||||
}
|
||||
names = append(names, strings.TrimSuffix(f.Name, ".yaml"))
|
||||
return
|
||||
})
|
||||
return
|
||||
}
|
||||
|
||||
func (d *Defaults) treeAt(rev string) (tree *object.Tree, err error) {
|
||||
h, err := d.repo.ResolveRevision(plumbing.Revision(rev))
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
obj, err := d.repo.Object(plumbing.AnyObject, *h)
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
for {
|
||||
switch o := obj.(type) {
|
||||
case *object.Tag: // tag -> commit
|
||||
obj, err = o.Object()
|
||||
|
||||
case *object.Commit: // commit -> tree
|
||||
return o.Tree()
|
||||
|
||||
default:
|
||||
err = object.ErrUnsupportedObject
|
||||
}
|
||||
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func (d *Defaults) decodeDefault(rev, filePath string, value Rev) (err error) {
|
||||
ba, err := d.ReadAll(rev, filePath)
|
||||
|
||||
if err != nil {
|
||||
return
|
||||
}
|
||||
|
||||
return yaml.Unmarshal(ba, value)
|
||||
}
|
Reference in New Issue
Block a user