etcd: decouple embedded etcd instance startup

This refactor changes how we instantiate the etcd based Backend to allow
separate initialization and startup for the embedded instance.
This commit is contained in:
Andras Banki-Horvath 2021-02-09 17:44:43 +01:00
parent 6757e14998
commit 9992e5c0b5
No known key found for this signature in database
GPG Key ID: 80E5375C094198D8
5 changed files with 46 additions and 47 deletions

@ -1,6 +1,7 @@
package kvdb
import (
"context"
"encoding/binary"
"fmt"
"io/ioutil"
@ -253,7 +254,14 @@ func GetTestBackend(path, name string) (Backend, func(), error) {
}
return db, empty, nil
} else if TestBackend == EtcdBackendName {
return GetEtcdTestBackend(path, 0, 0)
etcdConfig, cancel, err := StartEtcdTestBackend(path, 0, 0)
if err != nil {
return nil, empty, err
}
backend, err := Open(
EtcdBackendName, context.TODO(), etcdConfig,
)
return backend, cancel, err
}
return nil, nil, fmt.Errorf("unknown backend")

@ -3,8 +3,6 @@
package kvdb
import (
"context"
"github.com/lightningnetwork/lnd/channeldb/kvdb/etcd"
)
@ -12,33 +10,12 @@ import (
// defined, allowing testing our database code with etcd backend.
const TestBackend = EtcdBackendName
// GetEtcdBackend returns an etcd backend configured according to the
// passed etcdConfig.
func GetEtcdBackend(ctx context.Context, etcdConfig *etcd.Config) (
Backend, error) {
return Open(EtcdBackendName, etcdConfig)
}
// GetEtcdTestBackend creates an embedded etcd backend for testing
// storig the database at the passed path.
func GetEtcdTestBackend(path string, clientPort, peerPort uint16) (
Backend, func(), error) {
func StartEtcdTestBackend(path string, clientPort, peerPort uint16) (
*etcd.Config, func(), error) {
empty := func() {}
config, cleanup, err := etcd.NewEmbeddedEtcdInstance(
return etcd.NewEmbeddedEtcdInstance(
path, clientPort, peerPort,
)
if err != nil {
return nil, empty, err
}
backend, err := Open(EtcdBackendName, context.Background(), config)
if err != nil {
cleanup()
return nil, empty, err
}
return backend, cleanup, nil
}

@ -3,7 +3,6 @@
package kvdb
import (
"context"
"fmt"
"github.com/lightningnetwork/lnd/channeldb/kvdb/etcd"
@ -15,17 +14,9 @@ const TestBackend = BoltBackendName
var errEtcdNotAvailable = fmt.Errorf("etcd backend not available")
// GetEtcdBackend is a stub returning nil and errEtcdNotAvailable error.
func GetEtcdBackend(ctx context.Context, etcdConfig *etcd.Config) (
Backend, error) {
return nil, errEtcdNotAvailable
}
// GetTestEtcdBackend is a stub returning nil, an empty closure and an
// errEtcdNotAvailable error.
func GetEtcdTestBackend(path string, clientPort, peerPort uint16) (
Backend, func(), error) {
// StartEtcdTestBackend is a stub returning nil, and errEtcdNotAvailable error.
func StartEtcdTestBackend(path string, clientPort, peerPort uint16) (
*etcd.Config, func(), error) {
return nil, func() {}, errEtcdNotAvailable
}

@ -57,6 +57,27 @@ func (db *DB) Validate() error {
return nil
}
// Init should be called upon start to pre-initialize database access dependent
// on configuration.
func (db *DB) Init(ctx context.Context, dbPath string) error {
// Start embedded etcd server if requested.
if db.Backend == EtcdBackend && db.Etcd.Embedded {
cfg, _, err := kvdb.StartEtcdTestBackend(
dbPath, db.Etcd.EmbeddedClientPort,
db.Etcd.EmbeddedPeerPort,
)
if err != nil {
return err
}
// Override the original config with the config for
// the embedded instance.
db.Etcd = cfg
}
return nil
}
// DatabaseBackends is a two-tuple that holds the set of active database
// backends for the daemon. The two backends we expose are the local database
// backend, and the remote backend. The LocalDB attribute will always be
@ -83,14 +104,9 @@ func (db *DB) GetBackends(ctx context.Context, dbPath string) (
)
if db.Backend == EtcdBackend {
if db.Etcd.Embedded {
remoteDB, _, err = kvdb.GetEtcdTestBackend(
dbPath, db.Etcd.EmbeddedClientPort,
db.Etcd.EmbeddedPeerPort,
)
} else {
remoteDB, err = kvdb.GetEtcdBackend(ctx, db.Etcd)
}
remoteDB, err = kvdb.Open(
kvdb.EtcdBackendName, ctx, db.Etcd,
)
if err != nil {
return nil, err
}

7
lnd.go

@ -234,6 +234,13 @@ func Main(cfg *Config, lisCfg ListenerCfg, interceptor signal.Interceptor) error
ctx, cancel := context.WithCancel(ctx)
defer cancel()
// Run configuration dependent DB pre-initialization. Note that this
// needs to be done early and once during the startup process, before
// any DB access.
if err := cfg.DB.Init(ctx, cfg.localDatabaseDir()); err != nil {
return err
}
localChanDB, remoteChanDB, cleanUp, err := initializeDatabases(ctx, cfg)
switch {
case err == channeldb.ErrDryRunMigrationOK: