54 lines
1.8 KiB
Go
54 lines
1.8 KiB
Go
package app
|
|
|
|
import (
|
|
"bytes"
|
|
"io"
|
|
"os"
|
|
"strings"
|
|
|
|
"git.sendico.io/tech/sxchnge/notifications/email"
|
|
db "git.sendico.io/tech/sxchnge/shared/database"
|
|
merrors "git.sendico.io/tech/sxchnge/shared/errors"
|
|
"git.sendico.io/tech/sxchnge/shared/messaging"
|
|
"gopkg.in/yaml.v3"
|
|
)
|
|
|
|
type Config struct {
|
|
Messaging messaging.Config `yaml:"messaging"`
|
|
Listen string `yaml:"listen"`
|
|
TLSCert string `yaml:"tls_cert"`
|
|
TLSKey string `yaml:"tls_key"`
|
|
Database db.Config `yaml:"database"`
|
|
Templates string `yaml:"templates"`
|
|
Callers map[string]string `yaml:"callers"` // caller -> token environment variable
|
|
Email email.Config `yaml:"email"`
|
|
}
|
|
|
|
func Load(path string) (Config, error) {
|
|
var c Config
|
|
data, err := os.ReadFile(path)
|
|
if err != nil {
|
|
return c, merrors.OpaqueWrap(merrors.ErrInvalidArg, err, "cannot read configuration")
|
|
}
|
|
decoder := yaml.NewDecoder(bytes.NewReader(data))
|
|
decoder.KnownFields(true)
|
|
if err = decoder.Decode(&c); err != nil {
|
|
return c, merrors.InvalidArgument("invalid configuration")
|
|
}
|
|
if err = decoder.Decode(new(any)); err != io.EOF {
|
|
return c, merrors.InvalidArgument("unexpected configuration content")
|
|
}
|
|
if c.Listen == "" || c.TLSCert == "" || c.TLSKey == "" || c.Database.Driver != db.Mongo || c.Messaging.Driver != messaging.BBNats || c.Templates == "" || len(c.Callers) == 0 {
|
|
return c, merrors.InvalidArgument("missing notification configuration")
|
|
}
|
|
seen := map[string]bool{}
|
|
for caller, env := range c.Callers {
|
|
token := os.Getenv(env)
|
|
if strings.TrimSpace(caller) == "" || len(strings.TrimSpace(token)) < 32 || seen[token] {
|
|
return c, merrors.InvalidArgument("caller credentials must be unique and at least 32 bytes")
|
|
}
|
|
seen[token] = true
|
|
}
|
|
return c, nil
|
|
}
|