isle/go/daemon/daemon_test.go

228 lines
5.3 KiB
Go

package daemon
import (
"context"
"isle/bootstrap"
"isle/daemon/daecommon"
"isle/daemon/network"
"isle/toolkit"
"testing"
"dev.mediocregopher.com/mediocre-go-lib.git/mlog"
"github.com/stretchr/testify/assert"
"github.com/stretchr/testify/require"
)
type expectNetworkLoad struct {
creationParams bootstrap.CreationParams
networkConfig *daecommon.NetworkConfig
network *network.MockNetwork
}
type harnessOpts struct {
config daecommon.Config
expectNetworksLoaded []expectNetworkLoad
}
func (o *harnessOpts) withDefaults() *harnessOpts {
if o == nil {
o = new(harnessOpts)
}
return o
}
type harness struct {
ctx context.Context
networkLoader *network.MockLoader
daemon *Daemon
}
func newHarness(t *testing.T, opts *harnessOpts) *harness {
t.Parallel()
opts = opts.withDefaults()
var (
ctx = context.Background()
logger = toolkit.NewTestLogger(t)
networkLoader = network.NewMockLoader(t)
)
expectLoadable := make(
[]bootstrap.CreationParams, len(opts.expectNetworksLoaded),
)
for i, expectNetworkLoaded := range opts.expectNetworksLoaded {
expectLoadable[i] = expectNetworkLoaded.creationParams
networkLoader.
On(
"Load",
toolkit.MockArg[context.Context](),
toolkit.MockArg[*mlog.Logger](),
expectNetworkLoaded.creationParams,
&network.Opts{
Config: expectNetworkLoaded.networkConfig,
},
).
Return(expectNetworkLoaded.network, nil).
Once()
expectNetworkLoaded.network.On("Shutdown").Return(nil).Once()
}
networkLoader.
On("Loadable", toolkit.MockArg[context.Context]()).
Return(expectLoadable, nil).
Once()
daemon, err := New(ctx, logger, networkLoader, opts.config)
require.NoError(t, err)
t.Cleanup(func() {
t.Log("Shutting down Daemon")
assert.NoError(t, daemon.Shutdown())
})
return &harness{ctx, networkLoader, daemon}
}
func TestNew(t *testing.T) {
t.Run("no networks loaded", func(t *testing.T) {
_ = newHarness(t, nil)
})
t.Run("DEPRECATED network config matching", func(t *testing.T) {
var (
creationParams = bootstrap.NewCreationParams("AAA", "a.com")
networkConfig = daecommon.NewNetworkConfig(func(c *daecommon.NetworkConfig) {
c.DNS.Resolvers = []string{"foo"}
})
config = daecommon.Config{
Networks: map[string]daecommon.NetworkConfig{
daecommon.DeprecatedNetworkID: networkConfig,
},
}
)
_ = newHarness(t, &harnessOpts{
config: config,
expectNetworksLoaded: []expectNetworkLoad{
{
creationParams,
&networkConfig,
network.NewMockNetwork(t),
},
},
})
})
t.Run("network config matching", func(t *testing.T) {
var (
creationParamsA = bootstrap.NewCreationParams("AAA", "a.com")
creationParamsB = bootstrap.NewCreationParams("BBB", "b.com")
creationParamsC = bootstrap.NewCreationParams("CCC", "c.com")
creationParamsD = bootstrap.NewCreationParams("DDD", "d.com")
networkConfigA = daecommon.NewNetworkConfig(func(c *daecommon.NetworkConfig) {
c.DNS.Resolvers = []string{"foo"}
})
networkConfigB = daecommon.NewNetworkConfig(func(c *daecommon.NetworkConfig) {
c.VPN.Tun.Device = "bar"
})
networkConfigC = daecommon.NewNetworkConfig(func(c *daecommon.NetworkConfig) {
c.Storage.Allocations = []daecommon.ConfigStorageAllocation{
{
DataPath: "/path/data",
MetaPath: "/path/meta",
Capacity: 1,
},
}
})
config = daecommon.Config{
Networks: map[string]daecommon.NetworkConfig{
creationParamsA.ID: networkConfigA,
creationParamsB.Name: networkConfigB,
creationParamsC.Domain: networkConfigC,
"unknown": {},
},
}
)
_ = newHarness(t, &harnessOpts{
config: config,
expectNetworksLoaded: []expectNetworkLoad{
{
creationParamsA,
&networkConfigA,
network.NewMockNetwork(t),
},
{
creationParamsB,
&networkConfigB,
network.NewMockNetwork(t),
},
{
creationParamsC,
&networkConfigC,
network.NewMockNetwork(t),
},
{
creationParamsD,
nil,
network.NewMockNetwork(t),
},
},
})
})
}
func TestDaemon_SetConfig(t *testing.T) {
t.Run("success", func(t *testing.T) {
var (
networkA = network.NewMockNetwork(t)
h = newHarness(t, &harnessOpts{
expectNetworksLoaded: []expectNetworkLoad{{
bootstrap.NewCreationParams("AAA", "a.com"), nil, networkA,
}},
})
networkConfig = daecommon.NewNetworkConfig(func(c *daecommon.NetworkConfig) {
c.VPN.Tun.Device = "foo"
})
)
networkA.
On("SetConfig", toolkit.MockArg[context.Context](), networkConfig).
Return(nil).
Once()
err := h.daemon.SetConfig(h.ctx, networkConfig)
assert.NoError(t, err)
})
t.Run("ErrUserManagedNetworkConfig", func(t *testing.T) {
var (
creationParams = bootstrap.NewCreationParams("AAA", "a.com")
networkA = network.NewMockNetwork(t)
networkConfig = daecommon.NewNetworkConfig(nil)
h = newHarness(t, &harnessOpts{
config: daecommon.Config{
Networks: map[string]daecommon.NetworkConfig{
creationParams.Name: networkConfig,
},
},
expectNetworksLoaded: []expectNetworkLoad{
{creationParams, &networkConfig, networkA},
},
})
)
networkConfig.VPN.Tun.Device = "foo"
err := h.daemon.SetConfig(h.ctx, networkConfig)
assert.ErrorIs(t, err, ErrUserManagedNetworkConfig)
})
}