From 0b783c374a633df30d28316e5a572285070fb9fa Mon Sep 17 00:00:00 2001 From: William Petit Date: Fri, 24 Mar 2023 23:17:55 +0100 Subject: [PATCH] feat(controller,sysupgrade): openwrt upgrade controller --- cmd/agent/main.go | 2 + cmd/server/main.go | 5 +- go.mod | 1 - go.sum | 2 - internal/agent/controller/app/server.go | 3 +- internal/agent/controller/openwrt/hash.go | 31 +++ .../openwrt/spec/sysupgrade/init.go | 17 ++ .../openwrt/spec/sysupgrade/schema.json | 20 ++ .../openwrt/spec/sysupgrade/spec.go | 38 ++++ .../spec/sysupgrade/testdata/spec-ok.json | 9 + .../openwrt/spec/sysupgrade/validator_test.go | 65 +++++++ .../openwrt/sysupgrade_controller.go | 177 ++++++++++++++++++ .../openwrt/sysupgrade_firmware_version.go | 46 +++++ .../controller/openwrt/sysupgrade_options.go | 58 ++++++ .../command/agent/openwrt/uci/transform.go | 1 - internal/command/agent/run.go | 23 +++ internal/command/api/agent/spec/update.go | 5 - internal/command/api/root.go | 4 - internal/command/config/dump.go | 1 - internal/command/main.go | 4 - internal/command/server/run.go | 1 - internal/config/agent.go | 14 ++ internal/imports/format/format_import.go | 6 + internal/imports/passwd/passwd_import.go | 6 + internal/imports/spec/spec_import.go | 8 + internal/imports/sql/sql_import.go | 6 + internal/server/spec_api.go | 5 - modd.conf | 1 + 28 files changed, 531 insertions(+), 28 deletions(-) create mode 100644 internal/agent/controller/openwrt/hash.go create mode 100644 internal/agent/controller/openwrt/spec/sysupgrade/init.go create mode 100644 internal/agent/controller/openwrt/spec/sysupgrade/schema.json create mode 100644 internal/agent/controller/openwrt/spec/sysupgrade/spec.go create mode 100644 internal/agent/controller/openwrt/spec/sysupgrade/testdata/spec-ok.json create mode 100644 internal/agent/controller/openwrt/spec/sysupgrade/validator_test.go create mode 100644 internal/agent/controller/openwrt/sysupgrade_controller.go create mode 100644 internal/agent/controller/openwrt/sysupgrade_firmware_version.go create mode 100644 internal/agent/controller/openwrt/sysupgrade_options.go create mode 100644 internal/imports/format/format_import.go create mode 100644 internal/imports/passwd/passwd_import.go create mode 100644 internal/imports/spec/spec_import.go create mode 100644 internal/imports/sql/sql_import.go diff --git a/cmd/agent/main.go b/cmd/agent/main.go index 4d541a8..102c049 100644 --- a/cmd/agent/main.go +++ b/cmd/agent/main.go @@ -6,6 +6,8 @@ import ( "forge.cadoles.com/Cadoles/emissary/internal/command" "forge.cadoles.com/Cadoles/emissary/internal/command/agent" "forge.cadoles.com/Cadoles/emissary/internal/command/api" + + _ "forge.cadoles.com/Cadoles/emissary/internal/imports/spec" ) // nolint: gochecknoglobals diff --git a/cmd/server/main.go b/cmd/server/main.go index 553fc87..17cd8df 100644 --- a/cmd/server/main.go +++ b/cmd/server/main.go @@ -7,8 +7,9 @@ import ( "forge.cadoles.com/Cadoles/emissary/internal/command/api" "forge.cadoles.com/Cadoles/emissary/internal/command/server" - _ "github.com/jackc/pgx/v5/stdlib" - _ "modernc.org/sqlite" + _ "forge.cadoles.com/Cadoles/emissary/internal/imports/format" + _ "forge.cadoles.com/Cadoles/emissary/internal/imports/spec" + _ "forge.cadoles.com/Cadoles/emissary/internal/imports/sql" ) // nolint: gochecknoglobals diff --git a/go.mod b/go.mod index 6f1c43c..178c347 100644 --- a/go.mod +++ b/go.mod @@ -22,7 +22,6 @@ require ( github.com/mitchellh/mapstructure v1.5.0 github.com/pkg/errors v0.9.1 github.com/qri-io/jsonschema v0.2.1 - github.com/santhosh-tekuri/jsonschema/v5 v5.1.1 github.com/urfave/cli/v2 v2.24.4 gitlab.com/wpetit/goweb v0.0.0-20230227162855-a1f09bafccb3 gopkg.in/yaml.v3 v3.0.1 diff --git a/go.sum b/go.sum index cb3ccdc..0152916 100644 --- a/go.sum +++ b/go.sum @@ -1169,8 +1169,6 @@ github.com/rwtodd/Go.Sed v0.0.0-20210816025313-55464686f9ef/go.mod h1:8AEUvGVi2u github.com/ryanuber/columnize v0.0.0-20160712163229-9b3edd62028f/go.mod h1:sm1tb6uqfes/u+d4ooFouqFdy9/2g9QGwK3SQygK0Ts= github.com/safchain/ethtool v0.0.0-20190326074333-42ed695e3de8/go.mod h1:Z0q5wiBQGYcxhMZ6gUqHn6pYNLypFAvaL3UvgZLR0U4= github.com/safchain/ethtool v0.0.0-20210803160452-9aa261dae9b1/go.mod h1:Z0q5wiBQGYcxhMZ6gUqHn6pYNLypFAvaL3UvgZLR0U4= -github.com/santhosh-tekuri/jsonschema/v5 v5.1.1 h1:lEOLY2vyGIqKWUI9nzsOJRV3mb3WC9dXYORsLEUcoeY= -github.com/santhosh-tekuri/jsonschema/v5 v5.1.1/go.mod h1:FKdcjfQW6rpZSnxxUvEA5H/cDPdvJ/SZJQLWWXWGrZ0= github.com/satori/go.uuid v1.2.0/go.mod h1:dA0hQrYB0VpLJoorglMZABFdXlWrHn1NEOzdhQKdks0= github.com/sclevine/agouti v3.0.0+incompatible/go.mod h1:b4WX9W9L1sfQKXeJf1mUTLZKJ48R1S7H23Ji7oFO5Bw= github.com/sclevine/spec v1.2.0/go.mod h1:W4J29eT/Kzv7/b9IWLB055Z+qvVC9vt0Arko24q7p+U= diff --git a/internal/agent/controller/app/server.go b/internal/agent/controller/app/server.go index ec1d5a5..fd9ed6b 100644 --- a/internal/agent/controller/app/server.go +++ b/internal/agent/controller/app/server.go @@ -28,8 +28,7 @@ import ( "github.com/lestrrat-go/jwx/v2/jwk" "github.com/pkg/errors" - _ "forge.cadoles.com/arcad/edge/pkg/module/auth/http/passwd/argon2id" - _ "forge.cadoles.com/arcad/edge/pkg/module/auth/http/passwd/plain" + _ "forge.cadoles.com/Cadoles/emissary/internal/imports/passwd" ) type Server struct { diff --git a/internal/agent/controller/openwrt/hash.go b/internal/agent/controller/openwrt/hash.go new file mode 100644 index 0000000..487a122 --- /dev/null +++ b/internal/agent/controller/openwrt/hash.go @@ -0,0 +1,31 @@ +package openwrt + +import ( + "crypto/sha256" + "encoding/hex" + "io" + "os" + + "github.com/pkg/errors" +) + +func hash(path string) (string, error) { + file, err := os.Open(path) + if err != nil { + return "", errors.WithStack(err) + } + + hasher := sha256.New() + + defer func() { + if err := file.Close(); err != nil { + panic(errors.WithStack(err)) + } + }() + + if _, err := io.Copy(hasher, file); err != nil { + return "", errors.WithStack(err) + } + + return hex.EncodeToString(hasher.Sum(nil)), nil +} diff --git a/internal/agent/controller/openwrt/spec/sysupgrade/init.go b/internal/agent/controller/openwrt/spec/sysupgrade/init.go new file mode 100644 index 0000000..f3d3b71 --- /dev/null +++ b/internal/agent/controller/openwrt/spec/sysupgrade/init.go @@ -0,0 +1,17 @@ +package sysupgrade + +import ( + _ "embed" + + "forge.cadoles.com/Cadoles/emissary/internal/spec" + "github.com/pkg/errors" +) + +//go:embed schema.json +var schema []byte + +func init() { + if err := spec.Register(Name, schema); err != nil { + panic(errors.WithStack(err)) + } +} diff --git a/internal/agent/controller/openwrt/spec/sysupgrade/schema.json b/internal/agent/controller/openwrt/spec/sysupgrade/schema.json new file mode 100644 index 0000000..eef8941 --- /dev/null +++ b/internal/agent/controller/openwrt/spec/sysupgrade/schema.json @@ -0,0 +1,20 @@ +{ + "$schema": "https://json-schema.org/draft/2020-12/schema", + "$id": "https://sysupgrade.openwrt.emissary.cadoles.com/spec.json", + "title": "SysUpgradeSpec", + "description": "Emissary 'SysUpgrade' specification", + "type": "object", + "properties": { + "url": { + "type": "string" + }, + "sha256sum": { + "type": "string" + }, + "version": { + "type": "string" + } + }, + "required": ["url", "sha256sum", "version"], + "additionalProperties": false +} \ No newline at end of file diff --git a/internal/agent/controller/openwrt/spec/sysupgrade/spec.go b/internal/agent/controller/openwrt/spec/sysupgrade/spec.go new file mode 100644 index 0000000..ca0559d --- /dev/null +++ b/internal/agent/controller/openwrt/spec/sysupgrade/spec.go @@ -0,0 +1,38 @@ +package sysupgrade + +import ( + "forge.cadoles.com/Cadoles/emissary/internal/spec" +) + +const Name spec.Name = "sysupgrade.openwrt.emissary.cadoles.com" + +type Spec struct { + Revision int `json:"revision"` + URL string `json:"url"` + SHA256Sum string `json:"sha256sum"` + Version string `json:"version"` +} + +func (s *Spec) SpecName() spec.Name { + return Name +} + +func (s *Spec) SpecRevision() int { + return s.Revision +} + +func (s *Spec) SpecData() map[string]any { + return map[string]any{ + "url": s.URL, + "version": s.Version, + "sha256sum": s.SHA256Sum, + } +} + +func NewSpec() *Spec { + return &Spec{ + Revision: -1, + } +} + +var _ spec.Spec = &Spec{} diff --git a/internal/agent/controller/openwrt/spec/sysupgrade/testdata/spec-ok.json b/internal/agent/controller/openwrt/spec/sysupgrade/testdata/spec-ok.json new file mode 100644 index 0000000..53ef748 --- /dev/null +++ b/internal/agent/controller/openwrt/spec/sysupgrade/testdata/spec-ok.json @@ -0,0 +1,9 @@ +{ + "name": "sysupgrade.openwrt.emissary.cadoles.com", + "data": { + "url": "http://example.com/firmware.img", + "sha256sum": "58019192dacdae17755707719707db007e26dac856102280583fbd18427dd352", + "version": "0.0.0" + }, + "revision": 0 +} \ No newline at end of file diff --git a/internal/agent/controller/openwrt/spec/sysupgrade/validator_test.go b/internal/agent/controller/openwrt/spec/sysupgrade/validator_test.go new file mode 100644 index 0000000..7ce6e88 --- /dev/null +++ b/internal/agent/controller/openwrt/spec/sysupgrade/validator_test.go @@ -0,0 +1,65 @@ +package sysupgrade + +import ( + "context" + "encoding/json" + "io/ioutil" + "testing" + + "forge.cadoles.com/Cadoles/emissary/internal/spec" + "github.com/pkg/errors" +) + +type validatorTestCase struct { + Name string + Source string + ShouldFail bool +} + +var validatorTestCases = []validatorTestCase{ + { + Name: "SpecOK", + Source: "testdata/spec-ok.json", + ShouldFail: false, + }, +} + +func TestValidator(t *testing.T) { + t.Parallel() + + validator := spec.NewValidator() + if err := validator.Register(Name, schema); err != nil { + t.Fatalf("+%v", errors.WithStack(err)) + } + + for _, tc := range validatorTestCases { + func(tc validatorTestCase) { + t.Run(tc.Name, func(t *testing.T) { + t.Parallel() + + rawSpec, err := ioutil.ReadFile(tc.Source) + if err != nil { + t.Fatalf("+%v", errors.WithStack(err)) + } + + var spec spec.RawSpec + + if err := json.Unmarshal(rawSpec, &spec); err != nil { + t.Fatalf("+%v", errors.WithStack(err)) + } + + ctx := context.Background() + + err = validator.Validate(ctx, &spec) + + if !tc.ShouldFail && err != nil { + t.Errorf("+%v", errors.WithStack(err)) + } + + if tc.ShouldFail && err == nil { + t.Error("validation should have failed") + } + }) + }(tc) + } +} diff --git a/internal/agent/controller/openwrt/sysupgrade_controller.go b/internal/agent/controller/openwrt/sysupgrade_controller.go new file mode 100644 index 0000000..ebb1001 --- /dev/null +++ b/internal/agent/controller/openwrt/sysupgrade_controller.go @@ -0,0 +1,177 @@ +package openwrt + +import ( + "context" + "io" + "net/http" + "os" + "os/exec" + "path/filepath" + "strings" + + "forge.cadoles.com/Cadoles/emissary/internal/agent" + "forge.cadoles.com/Cadoles/emissary/internal/agent/controller/openwrt/spec/sysupgrade" + "github.com/pkg/errors" + "gitlab.com/wpetit/goweb/logger" +) + +type SysUpgradeController struct { + client *http.Client + command string + args []string + firmwareVersion FirmwareVersion +} + +// Name implements agent.Controller +func (*SysUpgradeController) Name() string { + return "sysupgrade-controller" +} + +// Reconcile implements agent.Controller +func (c *SysUpgradeController) Reconcile(ctx context.Context, state *agent.State) error { + sysSpec := sysupgrade.NewSpec() + + if err := state.GetSpec(sysupgrade.Name, sysSpec); err != nil { + if errors.Is(err, agent.ErrSpecNotFound) { + logger.Info(ctx, "could not find sysupgrade spec, doing nothing") + + return nil + } + + return errors.WithStack(err) + } + + firmwareVersion, err := c.firmwareVersion.FirmwareVersion(ctx) + if err != nil { + return errors.WithStack(err) + } + + ctx = logger.With(ctx, + logger.F("currentFirmwareVersion", firmwareVersion), + logger.F("newFirmwareVersion", sysSpec.Version), + ) + + if firmwareVersion == sysSpec.Version { + logger.Info(ctx, "firmware version did not change, doing nothing") + + return nil + } + + downloadDir, err := os.MkdirTemp(os.TempDir(), "emissary_sysupgrade_*") + if err != nil { + return errors.WithStack(err) + } + + defer func() { + if err := os.RemoveAll(downloadDir); err != nil { + logger.Error( + ctx, "could not remove download direction", + logger.E(errors.WithStack(err)), + logger.F("downloadDir", downloadDir), + ) + } + }() + + firmwareFile := filepath.Join(downloadDir, "firmware.bin") + + logger.Info( + ctx, "downloading firmware", + logger.F("url", sysSpec.URL), logger.F("sha256sum", sysSpec.SHA256Sum), + ) + + if err := c.downloadFile(ctx, sysSpec.URL, sysSpec.SHA256Sum, firmwareFile); err != nil { + return errors.WithStack(err) + } + + logger.Info(ctx, "upgrading firmware") + + if err := c.upgradeFirmware(ctx, firmwareFile); err != nil { + return errors.WithStack(err) + } + + return nil +} + +func (c *SysUpgradeController) downloadFile(ctx context.Context, url string, sha256sum string, dest string) error { + req, err := http.NewRequestWithContext(ctx, http.MethodGet, url, nil) + if err != nil { + return errors.WithStack(err) + } + + res, err := c.client.Do(req) + if err != nil { + return errors.WithStack(err) + } + + defer func() { + if err := res.Body.Close(); err != nil && !errors.Is(err, os.ErrClosed) { + panic(errors.WithStack(err)) + } + }() + + tmp, err := os.CreateTemp(filepath.Dir(dest), "download_") + if err != nil { + return errors.WithStack(err) + } + + defer func() { + if err := os.Remove(tmp.Name()); err != nil && !os.IsNotExist(err) { + panic(errors.WithStack(err)) + } + }() + + if _, err := io.Copy(tmp, res.Body); err != nil { + return errors.WithStack(err) + } + + tmpFileHash, err := hash(tmp.Name()) + if err != nil { + return errors.WithStack(err) + } + + if tmpFileHash != sha256sum { + return errors.Errorf("sha256 sum mismatch: expected '%s', got '%s'", sha256sum, tmpFileHash) + } + + if err := os.Rename(tmp.Name(), dest); err != nil { + return errors.WithStack(err) + } + + return nil +} + +func (c *SysUpgradeController) upgradeFirmware(ctx context.Context, firmwareFile string) error { + templatizedArgs := make([]string, len(c.args)) + for i, a := range c.args { + templatizedArgs[i] = strings.Replace(a, FirmwareFileTemplate, firmwareFile, 1) + } + + command := exec.CommandContext(ctx, c.command, templatizedArgs...) + + command.Stdout = os.Stdout + command.Stderr = os.Stderr + + logger.Debug(ctx, "executing command", logger.F("command", c.command), logger.F("args", templatizedArgs)) + + if err := command.Run(); err != nil { + return errors.WithStack(err) + } + + return nil +} + +func NewSysUpgradeController(funcs ...SysUpgradeOptionFunc) *SysUpgradeController { + opts := defaultSysUpgradeOptions() + for _, fn := range funcs { + fn(opts) + } + + return &SysUpgradeController{ + command: opts.Command, + args: opts.Args, + client: opts.Client, + firmwareVersion: opts.FirmwareVersion, + } +} + +var _ agent.Controller = &SysUpgradeController{} diff --git a/internal/agent/controller/openwrt/sysupgrade_firmware_version.go b/internal/agent/controller/openwrt/sysupgrade_firmware_version.go new file mode 100644 index 0000000..ac49457 --- /dev/null +++ b/internal/agent/controller/openwrt/sysupgrade_firmware_version.go @@ -0,0 +1,46 @@ +package openwrt + +import ( + "bytes" + "context" + "os" + "os/exec" + "strings" + + "github.com/pkg/errors" + "gitlab.com/wpetit/goweb/logger" +) + +type ShellFirmwareVersion struct { + command string + args []string +} + +// FirmwareVersion implements FirmwareVersion +func (fv *ShellFirmwareVersion) FirmwareVersion(ctx context.Context) (string, error) { + command := exec.CommandContext(ctx, fv.command, fv.args...) + + var buf bytes.Buffer + + command.Stdout = &buf + command.Stderr = os.Stderr + + logger.Debug(ctx, "executing command", logger.F("command", fv.command), logger.F("args", fv.args)) + + if err := command.Run(); err != nil { + return "", errors.WithStack(err) + } + + version := strings.TrimSpace(buf.String()) + + return version, nil +} + +func NewShellFirmwareVersion(command string, args ...string) *ShellFirmwareVersion { + return &ShellFirmwareVersion{ + command: command, + args: args, + } +} + +var _ FirmwareVersion = &ShellFirmwareVersion{} diff --git a/internal/agent/controller/openwrt/sysupgrade_options.go b/internal/agent/controller/openwrt/sysupgrade_options.go new file mode 100644 index 0000000..7d96f74 --- /dev/null +++ b/internal/agent/controller/openwrt/sysupgrade_options.go @@ -0,0 +1,58 @@ +package openwrt + +import ( + "context" + "net/http" + "time" +) + +const FirmwareFileTemplate = "%FIRMWARE%" + +type FirmwareVersion interface { + FirmwareVersion(context.Context) (string, error) +} + +type SysUpgradeOptions struct { + Command string + Args []string + FirmwareVersion FirmwareVersion + Client *http.Client +} + +func defaultSysUpgradeOptions() *SysUpgradeOptions { + return &SysUpgradeOptions{ + Command: `echo`, + Args: []string{`[DUMMY UPGRADE]`, FirmwareFileTemplate}, + Client: &http.Client{ + Timeout: 30 * time.Second, + }, + FirmwareVersion: NewShellFirmwareVersion(`echo`, "0.0.0-dummy"), + } +} + +type SysUpgradeOptionFunc func(*SysUpgradeOptions) + +func WithSysUpgradeCommand(command string, args ...string) SysUpgradeOptionFunc { + return func(opts *SysUpgradeOptions) { + opts.Command = command + opts.Args = args + } +} + +func WithSysUpgradeFirmwareVersion(firmwareVersion FirmwareVersion) SysUpgradeOptionFunc { + return func(opts *SysUpgradeOptions) { + opts.FirmwareVersion = firmwareVersion + } +} + +func WithSysUpgradeShellFirmwareVersion(command string, args ...string) SysUpgradeOptionFunc { + return func(opts *SysUpgradeOptions) { + opts.FirmwareVersion = NewShellFirmwareVersion(command, args...) + } +} + +func WithSysUpgradeClient(client *http.Client) SysUpgradeOptionFunc { + return func(opts *SysUpgradeOptions) { + opts.Client = client + } +} diff --git a/internal/command/agent/openwrt/uci/transform.go b/internal/command/agent/openwrt/uci/transform.go index a00d4db..de911de 100644 --- a/internal/command/agent/openwrt/uci/transform.go +++ b/internal/command/agent/openwrt/uci/transform.go @@ -10,7 +10,6 @@ import ( "forge.cadoles.com/Cadoles/emissary/internal/command/common" "forge.cadoles.com/Cadoles/emissary/internal/openwrt/uci" "github.com/pkg/errors" - _ "github.com/santhosh-tekuri/jsonschema/v5/httploader" "github.com/urfave/cli/v2" ) diff --git a/internal/command/agent/run.go b/internal/command/agent/run.go index a48bd2c..de83723 100644 --- a/internal/command/agent/run.go +++ b/internal/command/agent/run.go @@ -66,6 +66,29 @@ func RunCommand() *cli.Command { )) } + if ctrlConf.SysUpgrade.Enabled { + sysUpgradeArgs := make([]string, 0) + if len(ctrlConf.SysUpgrade.SysUpgradeCommand) > 1 { + sysUpgradeArgs = ctrlConf.SysUpgrade.SysUpgradeCommand[1:] + } + + firmwareVersionArgs := make([]string, 0) + if len(ctrlConf.SysUpgrade.FirmwareVersionCommand) > 1 { + firmwareVersionArgs = ctrlConf.SysUpgrade.FirmwareVersionCommand[1:] + } + + controllers = append(controllers, openwrt.NewSysUpgradeController( + openwrt.WithSysUpgradeCommand( + ctrlConf.SysUpgrade.SysUpgradeCommand[0], + sysUpgradeArgs..., + ), + openwrt.WithSysUpgradeShellFirmwareVersion( + ctrlConf.SysUpgrade.FirmwareVersionCommand[0], + firmwareVersionArgs..., + ), + )) + } + key, err := jwk.LoadOrGenerate(string(conf.Agent.PrivateKeyPath), jwk.DefaultKeySize) if err != nil { return errors.WithStack(err) diff --git a/internal/command/api/agent/spec/update.go b/internal/command/api/agent/spec/update.go index f752e31..2377b6c 100644 --- a/internal/command/api/agent/spec/update.go +++ b/internal/command/api/agent/spec/update.go @@ -13,11 +13,6 @@ import ( jsonpatch "github.com/evanphx/json-patch/v5" "github.com/pkg/errors" "github.com/urfave/cli/v2" - - // Import specs - _ "forge.cadoles.com/Cadoles/emissary/internal/spec/app" - _ "forge.cadoles.com/Cadoles/emissary/internal/spec/proxy" - _ "forge.cadoles.com/Cadoles/emissary/internal/spec/uci" ) func UpdateCommand() *cli.Command { diff --git a/internal/command/api/root.go b/internal/command/api/root.go index ebcdb32..261a6f7 100644 --- a/internal/command/api/root.go +++ b/internal/command/api/root.go @@ -3,10 +3,6 @@ package api import ( "forge.cadoles.com/Cadoles/emissary/internal/command/api/agent" "github.com/urfave/cli/v2" - - // Output format - _ "forge.cadoles.com/Cadoles/emissary/internal/format/json" - _ "forge.cadoles.com/Cadoles/emissary/internal/format/table" ) func Root() *cli.Command { diff --git a/internal/command/config/dump.go b/internal/command/config/dump.go index 118846b..34f6f2b 100644 --- a/internal/command/config/dump.go +++ b/internal/command/config/dump.go @@ -6,7 +6,6 @@ import ( "forge.cadoles.com/Cadoles/emissary/internal/command/common" "forge.cadoles.com/Cadoles/emissary/internal/config" "github.com/pkg/errors" - _ "github.com/santhosh-tekuri/jsonschema/v5/httploader" "github.com/urfave/cli/v2" "gitlab.com/wpetit/goweb/logger" ) diff --git a/internal/command/main.go b/internal/command/main.go index 0e05e19..dea056a 100644 --- a/internal/command/main.go +++ b/internal/command/main.go @@ -9,10 +9,6 @@ import ( "github.com/pkg/errors" "github.com/urfave/cli/v2" - - // Spec validation - _ "forge.cadoles.com/Cadoles/emissary/internal/spec/proxy" - _ "forge.cadoles.com/Cadoles/emissary/internal/spec/uci" ) func Main(buildDate, projectVersion, gitRef, defaultConfigPath string, commands ...*cli.Command) { diff --git a/internal/command/server/run.go b/internal/command/server/run.go index b5513e8..9e0662d 100644 --- a/internal/command/server/run.go +++ b/internal/command/server/run.go @@ -7,7 +7,6 @@ import ( "forge.cadoles.com/Cadoles/emissary/internal/command/common" "forge.cadoles.com/Cadoles/emissary/internal/server" "github.com/pkg/errors" - _ "github.com/santhosh-tekuri/jsonschema/v5/httploader" "github.com/urfave/cli/v2" "gitlab.com/wpetit/goweb/logger" ) diff --git a/internal/config/agent.go b/internal/config/agent.go index 7d7edd7..4771d40 100644 --- a/internal/config/agent.go +++ b/internal/config/agent.go @@ -1,5 +1,7 @@ package config +import "forge.cadoles.com/Cadoles/emissary/internal/agent/controller/openwrt" + type AgentConfig struct { ServerURL InterpolatedString `yaml:"serverUrl"` PrivateKeyPath InterpolatedString `yaml:"privateKeyPath"` @@ -20,6 +22,7 @@ type ControllersConfig struct { Proxy ProxyControllerConfig `yaml:"proxy"` UCI UCIControllerConfig `yaml:"uci"` App AppControllerConfig `yaml:"app"` + SysUpgrade SysUpgradeControllerConfig `yaml:"sysupgrade"` } type PersistenceControllerConfig struct { @@ -46,6 +49,12 @@ type AppControllerConfig struct { DownloadDir InterpolatedString `yaml:"downloadDir"` } +type SysUpgradeControllerConfig struct { + Enabled InterpolatedBool `yaml:"enabled"` + SysUpgradeCommand InterpolatedStringSlice `yaml:"sysupgradeCommand"` + FirmwareVersionCommand InterpolatedStringSlice `yaml:"firmwareVersionCommand"` +} + func NewDefaultAgentConfig() AgentConfig { return AgentConfig{ ServerURL: "http://127.0.0.1:3000", @@ -72,6 +81,11 @@ func NewDefaultAgentConfig() AgentConfig { DataDir: "apps/data", DownloadDir: "apps/bundles", }, + SysUpgrade: SysUpgradeControllerConfig{ + Enabled: true, + SysUpgradeCommand: InterpolatedStringSlice{"sysupgrade", "--force", "-u", "-v", openwrt.FirmwareFileTemplate}, + FirmwareVersionCommand: InterpolatedStringSlice{"sh", "-c", `source /etc/openwrt_release && echo "$DISTRIB_ID-$DISTRIB_RELEASE-$DISTRIB_REVISION"`}, + }, }, Collectors: []ShellCollectorConfig{ { diff --git a/internal/imports/format/format_import.go b/internal/imports/format/format_import.go new file mode 100644 index 0000000..0e3caa9 --- /dev/null +++ b/internal/imports/format/format_import.go @@ -0,0 +1,6 @@ +package format + +import ( + _ "forge.cadoles.com/Cadoles/emissary/internal/format/json" + _ "forge.cadoles.com/Cadoles/emissary/internal/format/table" +) diff --git a/internal/imports/passwd/passwd_import.go b/internal/imports/passwd/passwd_import.go new file mode 100644 index 0000000..509977f --- /dev/null +++ b/internal/imports/passwd/passwd_import.go @@ -0,0 +1,6 @@ +package passwd + +import ( + _ "forge.cadoles.com/arcad/edge/pkg/module/auth/http/passwd/argon2id" + _ "forge.cadoles.com/arcad/edge/pkg/module/auth/http/passwd/plain" +) diff --git a/internal/imports/spec/spec_import.go b/internal/imports/spec/spec_import.go new file mode 100644 index 0000000..6ec4588 --- /dev/null +++ b/internal/imports/spec/spec_import.go @@ -0,0 +1,8 @@ +package spec + +import ( + _ "forge.cadoles.com/Cadoles/emissary/internal/agent/controller/openwrt/spec/sysupgrade" + _ "forge.cadoles.com/Cadoles/emissary/internal/spec/app" + _ "forge.cadoles.com/Cadoles/emissary/internal/spec/proxy" + _ "forge.cadoles.com/Cadoles/emissary/internal/spec/uci" +) diff --git a/internal/imports/sql/sql_import.go b/internal/imports/sql/sql_import.go new file mode 100644 index 0000000..79bb1d8 --- /dev/null +++ b/internal/imports/sql/sql_import.go @@ -0,0 +1,6 @@ +package sql + +import ( + _ "github.com/jackc/pgx/v5/stdlib" + _ "modernc.org/sqlite" +) diff --git a/internal/server/spec_api.go b/internal/server/spec_api.go index b2c90b9..fa2fa21 100644 --- a/internal/server/spec_api.go +++ b/internal/server/spec_api.go @@ -10,11 +10,6 @@ import ( "github.com/pkg/errors" "gitlab.com/wpetit/goweb/api" "gitlab.com/wpetit/goweb/logger" - - // Import specs - _ "forge.cadoles.com/Cadoles/emissary/internal/spec/app" - _ "forge.cadoles.com/Cadoles/emissary/internal/spec/proxy" - _ "forge.cadoles.com/Cadoles/emissary/internal/spec/uci" ) const ( diff --git a/modd.conf b/modd.conf index ab5cbcc..38c3958 100644 --- a/modd.conf +++ b/modd.conf @@ -1,4 +1,5 @@ **/*.go +**/*.json modd.conf tmp/config.yml .env {