Skip to content

Commit

Permalink
agent: Refactor service and config
Browse files Browse the repository at this point in the history
This commit moves the services and agent's configuration in their own
module to improve readability.

Signed-off-by: Cosmin Tupangiu <[email protected]>
  • Loading branch information
tupyy committed Dec 5, 2024
1 parent 3d33aa9 commit 3006332
Show file tree
Hide file tree
Showing 13 changed files with 69 additions and 62 deletions.
7 changes: 4 additions & 3 deletions cmd/planner-agent/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ import (

"github.com/google/uuid"
"github.com/kubev2v/migration-planner/internal/agent"
"github.com/kubev2v/migration-planner/internal/agent/config"
"github.com/kubev2v/migration-planner/pkg/log"
"go.uber.org/zap"
"go.uber.org/zap/zapcore"
Expand All @@ -28,16 +29,16 @@ func main() {
}

type agentCmd struct {
config *agent.Config
config *config.Config
configFile string
}

func NewAgentCommand() *agentCmd {
a := &agentCmd{
config: agent.NewDefault(),
config: config.NewDefault(),
}

flag.StringVar(&a.configFile, "config", agent.DefaultConfigFile, "Path to the agent's configuration file.")
flag.StringVar(&a.configFile, "config", config.DefaultConfigFile, "Path to the agent's configuration file.")

flag.Usage = func() {
fmt.Fprintf(flag.CommandLine.Output(), "Usage of %s:\n", os.Args[0])
Expand Down
22 changes: 11 additions & 11 deletions internal/agent/agent.go
Original file line number Diff line number Diff line change
Expand Up @@ -14,14 +14,14 @@ import (
"github.com/google/uuid"
api "github.com/kubev2v/migration-planner/api/v1alpha1"
"github.com/kubev2v/migration-planner/internal/agent/client"
"github.com/kubev2v/migration-planner/internal/agent/config"
"github.com/kubev2v/migration-planner/internal/agent/service"
"github.com/lthibault/jitterbug"
"go.uber.org/zap"
utilruntime "k8s.io/apimachinery/pkg/util/runtime"
)

const (
// name of the file which stores the current inventory
InventoryFile = "inventory.json"
defaultAgentPort = 3333
)

Expand All @@ -31,7 +31,7 @@ const (
var version string

// New creates a new agent.
func New(id uuid.UUID, config *Config) *Agent {
func New(id uuid.UUID, config *config.Config) *Agent {
return &Agent{
config: config,
healtCheckStopCh: make(chan chan any),
Expand All @@ -40,7 +40,7 @@ func New(id uuid.UUID, config *Config) *Agent {
}

type Agent struct {
config *Config
config *config.Config
server *Server
healtCheckStopCh chan chan any
credUrl string
Expand Down Expand Up @@ -93,8 +93,8 @@ func (a *Agent) Stop() {
}

func (a *Agent) start(ctx context.Context, plannerClient client.Planner) {
inventoryUpdater := NewInventoryUpdater(a.id, plannerClient)
statusUpdater := NewStatusUpdater(a.id, version, a.credUrl, a.config, plannerClient)
inventoryUpdater := service.NewInventoryUpdater(a.id, plannerClient)
statusUpdater := service.NewStatusUpdater(a.id, version, a.credUrl, a.config, plannerClient)

// start server
a.server = NewServer(defaultAgentPort, a.config.DataDir, a.config.WwwDir)
Expand All @@ -104,7 +104,7 @@ func (a *Agent) start(ctx context.Context, plannerClient client.Planner) {
credUrl := a.initializeCredentialUrl()

// start the health check
healthChecker, err := NewHealthChecker(
healthChecker, err := service.NewHealthChecker(
plannerClient,
a.config.DataDir,
time.Duration(a.config.HealthCheckInterval*int64(time.Second)),
Expand All @@ -116,8 +116,8 @@ func (a *Agent) start(ctx context.Context, plannerClient client.Planner) {
// TODO refactor health checker to call it from the main goroutine
healthChecker.Start(a.healtCheckStopCh)

collector := NewCollector(a.config.DataDir)
collector.collect(ctx)
collector := service.NewCollector(a.config.DataDir)
collector.Collect(ctx)

updateTicker := jitterbug.New(time.Duration(a.config.UpdateInterval.Duration), &jitterbug.Norm{Stdev: 30 * time.Millisecond, Mean: 0})

Expand All @@ -140,7 +140,7 @@ func (a *Agent) start(ctx context.Context, plannerClient client.Planner) {
status, statusInfo, inventory := statusUpdater.CalculateStatus()

// check for health. Send requests only if we have connectivity
if healthChecker.State() == HealthCheckStateConsoleUnreachable {
if healthChecker.State() == service.HealthCheckStateConsoleUnreachable {
continue
}

Expand Down Expand Up @@ -190,7 +190,7 @@ func (a *Agent) initializeCredentialUrl() string {
return credUrl
}

func newPlannerClient(cfg *Config) (client.Planner, error) {
func newPlannerClient(cfg *config.Config) (client.Planner, error) {
httpClient, err := client.NewFromConfig(&cfg.PlannerService.Config)
if err != nil {
return nil, err
Expand Down
5 changes: 3 additions & 2 deletions internal/agent/agent_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ import (
agentapi "github.com/kubev2v/migration-planner/api/v1alpha1/agent"
"github.com/kubev2v/migration-planner/internal/agent"
"github.com/kubev2v/migration-planner/internal/agent/client"
"github.com/kubev2v/migration-planner/internal/agent/config"
"github.com/kubev2v/migration-planner/internal/util"
. "github.com/onsi/ginkgo/v2"
. "github.com/onsi/gomega"
Expand Down Expand Up @@ -64,8 +65,8 @@ var _ = Describe("Agent", func() {
Context("Agent", func() {
It("agents starts successfully -- status waiting-for-credentials", func() {
updateInterval, _ := time.ParseDuration("5s")
config := agent.Config{
PlannerService: agent.PlannerService{Config: *client.NewDefault()},
config := config.Config{
PlannerService: config.PlannerService{Config: *client.NewDefault()},
DataDir: agentTmpFolder,
ConfigDir: agentTmpFolder,
UpdateInterval: util.Duration{Duration: updateInterval},
Expand Down
13 changes: 12 additions & 1 deletion internal/agent/config.go → internal/agent/config/config.go
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
package agent
package config

import (
"encoding/json"
Expand All @@ -14,6 +14,10 @@ import (
)

const (
// name of the file which stores the source credentials
CredentialsFile = "credentials.json"
// name of the file which stores the current inventory
InventoryFile = "inventory.json"
// DefaultUpdateInterval is the default interval between two status updates
DefaultUpdateInterval = time.Duration(60 * time.Second)
// DefaultConfigDir is the default directory where the device's configuration is stored
Expand All @@ -32,6 +36,13 @@ const (
DefaultHealthCheck = 10
)

type Credentials struct {
URL string `json:"url"`
Username string `json:"username"`
Password string `json:"password"`
IsDataSharingAllowed bool `json:"isDataSharingAllowed"`
}

type Config struct {
// ConfigDir is the directory where the agent's configuration is stored
ConfigDir string `json:"config-dir"`
Expand Down
24 changes: 7 additions & 17 deletions internal/agent/rest.go
Original file line number Diff line number Diff line change
Expand Up @@ -13,20 +13,17 @@ import (
"github.com/go-chi/chi"
"github.com/go-chi/render"
liberr "github.com/konveyor/forklift-controller/pkg/lib/error"
"github.com/kubev2v/migration-planner/internal/agent/config"
"github.com/kubev2v/migration-planner/internal/agent/fileio"
"github.com/kubev2v/migration-planner/internal/agent/service"
"github.com/vmware/govmomi"
"github.com/vmware/govmomi/session"
"github.com/vmware/govmomi/vim25"
"github.com/vmware/govmomi/vim25/soap"
"go.uber.org/zap"
)

const (
// name of the file which stores the source credentials
CredentialsFile = "credentials.json"
)

func RegisterApi(router *chi.Mux, statusUpdater *StatusUpdater, dataDir string) {
func RegisterApi(router *chi.Mux, statusUpdater *service.StatusUpdater, dataDir string) {
router.Get("/api/v1/version", func(w http.ResponseWriter, r *http.Request) {
_ = render.Render(w, r, VersionReply{Version: version})
})
Expand Down Expand Up @@ -56,15 +53,8 @@ func (v VersionReply) Render(w http.ResponseWriter, r *http.Request) error {
return nil
}

type Credentials struct {
URL string `json:"url"`
Username string `json:"username"`
Password string `json:"password"`
IsDataSharingAllowed bool `json:"isDataSharingAllowed"`
}

func credentialHandler(dataDir string, w http.ResponseWriter, r *http.Request) {
credentials := &Credentials{}
credentials := &config.Credentials{}

err := json.NewDecoder(r.Body).Decode(credentials)
if err != nil {
Expand All @@ -84,7 +74,7 @@ func credentialHandler(dataDir string, w http.ResponseWriter, r *http.Request) {
return
}

credPath := filepath.Join(dataDir, CredentialsFile)
credPath := filepath.Join(dataDir, config.CredentialsFile)
buf, _ := json.Marshal(credentials)
writer := fileio.NewWriter()

Expand All @@ -98,7 +88,7 @@ func credentialHandler(dataDir string, w http.ResponseWriter, r *http.Request) {
w.WriteHeader(http.StatusNoContent)
}

func parseUrl(credentials *Credentials) (*url.URL, error) {
func parseUrl(credentials *config.Credentials) (*url.URL, error) {
u, err := url.ParseRequestURI(credentials.URL)
if err != nil {
return nil, err
Expand All @@ -111,7 +101,7 @@ func parseUrl(credentials *Credentials) (*url.URL, error) {
return u, nil
}

func testVmwareConnection(requestCtx context.Context, credentials *Credentials) (status int, err error) {
func testVmwareConnection(requestCtx context.Context, credentials *config.Credentials) (status int, err error) {
u, err := parseUrl(credentials)
if err != nil {
return http.StatusUnprocessableEntity, liberr.Wrap(err)
Expand Down
3 changes: 2 additions & 1 deletion internal/agent/server.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,7 @@ import (

"github.com/go-chi/chi"
"github.com/go-chi/chi/middleware"
"github.com/kubev2v/migration-planner/internal/agent/service"
"go.uber.org/zap"
)

Expand All @@ -32,7 +33,7 @@ func NewServer(port int, dataFolder, wwwFolder string) *Server {
}
}

func (s *Server) Start(statusUpdater *StatusUpdater) {
func (s *Server) Start(statusUpdater *service.StatusUpdater) {
router := chi.NewRouter()
router.Use(middleware.RequestID)
router.Use(middleware.Logger)
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
package agent
package service

import (
"bytes"
Expand All @@ -21,6 +21,7 @@ import (
web "github.com/konveyor/forklift-controller/pkg/controller/provider/web/vsphere"
libmodel "github.com/konveyor/forklift-controller/pkg/lib/inventory/model"
apiplanner "github.com/kubev2v/migration-planner/api/v1alpha1"
"github.com/kubev2v/migration-planner/internal/agent/config"
"github.com/kubev2v/migration-planner/internal/util"
"go.uber.org/zap"
core "k8s.io/api/core/v1"
Expand All @@ -38,7 +39,7 @@ func NewCollector(dataDir string) *Collector {
}
}

func (c *Collector) collect(ctx context.Context) {
func (c *Collector) Collect(ctx context.Context) {
c.once.Do(func() {
go func() {
for {
Expand All @@ -55,7 +56,7 @@ func (c *Collector) collect(ctx context.Context) {
}

func (c *Collector) run() {
credentialsFilePath := filepath.Join(c.dataDir, CredentialsFile)
credentialsFilePath := filepath.Join(c.dataDir, config.CredentialsFile)
zap.S().Named("collector").Infof("Waiting for credentials")
waitForFile(credentialsFilePath)

Expand All @@ -65,7 +66,7 @@ func (c *Collector) run() {
return
}

var creds Credentials
var creds config.Credentials
if err := json.Unmarshal(credsData, &creds); err != nil {
zap.S().Named("collector").Errorf("Error parsing credentials JSON: %v\n", err)
return
Expand Down Expand Up @@ -148,7 +149,7 @@ func (c *Collector) run() {
fillInventoryObjectWithMoreData(vms, inv)

zap.S().Named("collector").Infof("Write the inventory to output file")
if err := createOuput(filepath.Join(c.dataDir, InventoryFile), inv); err != nil {
if err := createOuput(filepath.Join(c.dataDir, config.InventoryFile), inv); err != nil {
zap.S().Named("collector").Errorf("Fill the inventory object with more data: %s", err)
return
}
Expand Down Expand Up @@ -239,7 +240,7 @@ func createBasicInventoryObj(vCenterID string, vms *[]vspheremodel.VM, collector
}
}

func getProvider(creds Credentials) *api.Provider {
func getProvider(creds config.Credentials) *api.Provider {
vsphereType := api.VSphere
return &api.Provider{
Spec: api.ProviderSpec{
Expand All @@ -249,7 +250,7 @@ func getProvider(creds Credentials) *api.Provider {
}
}

func getSecret(creds Credentials) *core.Secret {
func getSecret(creds config.Credentials) *core.Secret {
return &core.Secret{
ObjectMeta: meta.ObjectMeta{
Name: "vsphere-secret",
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
package agent
package service

import (
"context"
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
package agent
package service

import (
"bytes"
Expand Down
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
package agent
package service

import (
"bytes"
Expand Down
Original file line number Diff line number Diff line change
@@ -1,13 +1,13 @@
package agent_test
package service_test

import (
"context"

"github.com/google/uuid"
api "github.com/kubev2v/migration-planner/api/v1alpha1"
v1alpha1 "github.com/kubev2v/migration-planner/api/v1alpha1/agent"
"github.com/kubev2v/migration-planner/internal/agent"
"github.com/kubev2v/migration-planner/internal/agent/client"
"github.com/kubev2v/migration-planner/internal/agent/service"
. "github.com/onsi/ginkgo/v2"
. "github.com/onsi/gomega"
)
Expand Down Expand Up @@ -38,7 +38,7 @@ var _ = Describe("Inventory", func() {
Vms: api.VMs{Total: 2},
Vcenter: api.VCenter{Id: sourceID.String()},
}
inventoryUpdater := agent.NewInventoryUpdater(agentID, &client)
inventoryUpdater := service.NewInventoryUpdater(agentID, &client)
inventoryUpdater.UpdateServiceWithInventory(context.TODO(), inventory)
})
})
Expand Down
11 changes: 6 additions & 5 deletions internal/agent/status.go → internal/agent/service/status.go
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
package agent
package service

import (
"context"
Expand All @@ -11,6 +11,7 @@ import (
api "github.com/kubev2v/migration-planner/api/v1alpha1"
agentapi "github.com/kubev2v/migration-planner/api/v1alpha1/agent"
"github.com/kubev2v/migration-planner/internal/agent/client"
"github.com/kubev2v/migration-planner/internal/agent/config"
"github.com/kubev2v/migration-planner/internal/agent/fileio"
)

Expand All @@ -21,12 +22,12 @@ const (
type StatusUpdater struct {
agentID uuid.UUID
version string
config *Config
config *config.Config
client client.Planner
credUrl string
}

func NewStatusUpdater(agentID uuid.UUID, version, credUrl string, config *Config, client client.Planner) *StatusUpdater {
func NewStatusUpdater(agentID uuid.UUID, version, credUrl string, config *config.Config, client client.Planner) *StatusUpdater {
return &StatusUpdater{
client: client,
config: config,
Expand All @@ -52,8 +53,8 @@ func (s *StatusUpdater) UpdateStatus(ctx context.Context, status api.AgentStatus
}

func (s *StatusUpdater) CalculateStatus() (api.AgentStatus, string, *api.Inventory) {
inventoryFilePath := filepath.Join(s.config.DataDir, InventoryFile)
credentialsFilePath := filepath.Join(s.config.DataDir, CredentialsFile)
inventoryFilePath := filepath.Join(s.config.DataDir, config.InventoryFile)
credentialsFilePath := filepath.Join(s.config.DataDir, config.CredentialsFile)
reader := fileio.NewReader()

err := reader.CheckPathExists(credentialsFilePath)
Expand Down
Loading

0 comments on commit 3006332

Please sign in to comment.