135 lines
3.0 KiB
Go
135 lines
3.0 KiB
Go
|
// Copyright 2024 Matthew Rich <matthewrich.conf@gmail.com>. All rights reserved.
|
||
|
|
||
|
package config
|
||
|
|
||
|
import (
|
||
|
"context"
|
||
|
"encoding/json"
|
||
|
"fmt"
|
||
|
"io"
|
||
|
"gopkg.in/yaml.v3"
|
||
|
"log/slog"
|
||
|
"decl/internal/codec"
|
||
|
)
|
||
|
|
||
|
type BlockType struct {
|
||
|
Name string `json:"name" yaml:"name"`
|
||
|
Type TypeName `json:"type" yaml:"type"`
|
||
|
}
|
||
|
|
||
|
type Block struct {
|
||
|
Name string `json:"name" yaml:"name"`
|
||
|
Type TypeName `json:"type" yaml:"type"`
|
||
|
Values Configuration `json:"values" yaml:"values"`
|
||
|
}
|
||
|
|
||
|
func NewBlock() *Block {
|
||
|
return &Block{ Type: "generic" }
|
||
|
}
|
||
|
|
||
|
func (b *Block) Clone() *Block {
|
||
|
return &Block {
|
||
|
Type: b.Type,
|
||
|
Values: b.Values.Clone(),
|
||
|
}
|
||
|
}
|
||
|
|
||
|
func (b *Block) Load(r io.Reader) error {
|
||
|
return codec.NewYAMLDecoder(r).Decode(b)
|
||
|
}
|
||
|
|
||
|
func (b *Block) LoadBlock(yamlBlock string) (err error) {
|
||
|
err = codec.NewYAMLStringDecoder(yamlBlock).Decode(b)
|
||
|
slog.Info("LoadBlock()", "yaml", yamlBlock, "object", b, "err", err)
|
||
|
return
|
||
|
}
|
||
|
|
||
|
func (b *Block) NewConfiguration() error {
|
||
|
uri := fmt.Sprintf("%s://", b.Type)
|
||
|
newConfig, err := ConfigTypes.New(uri)
|
||
|
b.Values = newConfig
|
||
|
return err
|
||
|
}
|
||
|
|
||
|
func (b *Block) GetValue(key string) (any, error) {
|
||
|
return b.Values.GetValue(key)
|
||
|
}
|
||
|
|
||
|
func (b *Block) Configuration() Configuration {
|
||
|
return b.Values
|
||
|
}
|
||
|
|
||
|
func (b *Block) SetURI(uri string) (e error) {
|
||
|
b.Values = NewConfiguration(uri)
|
||
|
if b.Values == nil {
|
||
|
return ErrUnknownConfigurationType
|
||
|
}
|
||
|
b.Type = TypeName(b.Values.Type())
|
||
|
_,e = b.Values.Read(context.Background())
|
||
|
return e
|
||
|
}
|
||
|
|
||
|
|
||
|
func (b *Block) UnmarshalValue(value *BlockType) error {
|
||
|
b.Name = value.Name
|
||
|
if value.Type == "" {
|
||
|
b.Type = "generic"
|
||
|
} else {
|
||
|
b.Type = value.Type
|
||
|
}
|
||
|
|
||
|
newConfig, configErr := ConfigTypes.New(fmt.Sprintf("%s://", b.Type))
|
||
|
if configErr != nil {
|
||
|
return configErr
|
||
|
}
|
||
|
b.Values = newConfig
|
||
|
return nil
|
||
|
}
|
||
|
|
||
|
func (b *Block) UnmarshalYAML(value *yaml.Node) error {
|
||
|
t := &BlockType{}
|
||
|
if unmarshalConfigurationTypeErr := value.Decode(t); unmarshalConfigurationTypeErr != nil {
|
||
|
return unmarshalConfigurationTypeErr
|
||
|
}
|
||
|
|
||
|
if err := b.UnmarshalValue(t); err != nil {
|
||
|
return err
|
||
|
}
|
||
|
|
||
|
configurationVals := struct {
|
||
|
Values yaml.Node `json:"values"`
|
||
|
}{}
|
||
|
if unmarshalValuesErr := value.Decode(&configurationVals); unmarshalValuesErr != nil {
|
||
|
return unmarshalValuesErr
|
||
|
}
|
||
|
if unmarshalConfigurationErr := configurationVals.Values.Decode(b.Values); unmarshalConfigurationErr != nil {
|
||
|
return unmarshalConfigurationErr
|
||
|
}
|
||
|
_, readErr := b.Values.Read(context.Background())
|
||
|
return readErr
|
||
|
}
|
||
|
|
||
|
func (b *Block) UnmarshalJSON(data []byte) error {
|
||
|
t := &BlockType{}
|
||
|
if unmarshalConfigurationTypeErr := json.Unmarshal(data, t); unmarshalConfigurationTypeErr != nil {
|
||
|
return unmarshalConfigurationTypeErr
|
||
|
}
|
||
|
|
||
|
if err := b.UnmarshalValue(t); err != nil {
|
||
|
return err
|
||
|
}
|
||
|
|
||
|
configurationVals := struct {
|
||
|
Values Configuration `json:"values"`
|
||
|
}{Values: b.Values}
|
||
|
if unmarshalValuesErr := json.Unmarshal(data, &configurationVals); unmarshalValuesErr != nil {
|
||
|
return unmarshalValuesErr
|
||
|
}
|
||
|
_, readErr := b.Values.Read(context.Background())
|
||
|
return readErr
|
||
|
}
|
||
|
|
||
|
func (b *Block) MarshalYAML() (any, error) {
|
||
|
return b, nil
|
||
|
}
|