[#304] morph: Iterate endpoints when create ws client in constructor

Signed-off-by: Anton Nikiforov <an.nikiforov@yadro.com>
This commit is contained in:
Anton Nikiforov 2023-05-03 15:58:21 +03:00
parent 479c5a65e1
commit cedd07bbc8
3 changed files with 24 additions and 3 deletions

View file

@ -13,6 +13,7 @@ Changelog for FrostFS Node
- Read config files from dir even if config file not provided via `--config` for node (#238) - Read config files from dir even if config file not provided via `--config` for node (#238)
- Notary requests parsing according to `neo-go`'s updates (#268) - Notary requests parsing according to `neo-go`'s updates (#268)
- Tree service panic in its internal client cache (#322) - Tree service panic in its internal client cache (#322)
- Iterate over endpoints when create ws client in morph's constructor (#304)
### Removed ### Removed
### Updated ### Updated

View file

@ -413,6 +413,8 @@ const (
FrostFSIRInternalError = "internal error" // Info in ../node/cmd/frostfs-ir/main.go FrostFSIRInternalError = "internal error" // Info in ../node/cmd/frostfs-ir/main.go
FrostFSIRCouldNotShutdownHTTPServer = "could not shutdown HTTP server" // Debug in ../node/cmd/frostfs-ir/main.go FrostFSIRCouldNotShutdownHTTPServer = "could not shutdown HTTP server" // Debug in ../node/cmd/frostfs-ir/main.go
FrostFSIRApplicationStopped = "application stopped" // Info in ../node/cmd/frostfs-ir/main.go FrostFSIRApplicationStopped = "application stopped" // Info in ../node/cmd/frostfs-ir/main.go
FrostFSIRCouldntCreateRPCClientForEndpoint = "could not create RPC client for endpoint" // Debug in ../node/pkg/morph/client/constructor.go
FrostFSIRCreatedRPCClientForEndpoint = "created RPC client for endpoint" // Info in ../node/pkg/morph/client/constructor.go
FrostFSNodeCouldNotReadCertificateFromFile = "could not read certificate from file" // Error in ../node/cmd/frostfs-node/grpc.go FrostFSNodeCouldNotReadCertificateFromFile = "could not read certificate from file" // Error in ../node/cmd/frostfs-node/grpc.go
FrostFSNodeCantListenGRPCEndpoint = "can't listen gRPC endpoint" // Error in ../node/cmd/frostfs-node/grpc.go FrostFSNodeCantListenGRPCEndpoint = "can't listen gRPC endpoint" // Error in ../node/cmd/frostfs-node/grpc.go
FrostFSNodeStopListeningGRPCEndpoint = "stop listening gRPC endpoint" // Info in ../node/cmd/frostfs-node/grpc.go FrostFSNodeStopListeningGRPCEndpoint = "stop listening gRPC endpoint" // Info in ../node/cmd/frostfs-node/grpc.go

View file

@ -7,6 +7,7 @@ import (
"sync" "sync"
"time" "time"
"git.frostfs.info/TrueCloudLab/frostfs-node/internal/logs"
"git.frostfs.info/TrueCloudLab/frostfs-node/pkg/util/logger" "git.frostfs.info/TrueCloudLab/frostfs-node/pkg/util/logger"
lru "github.com/hashicorp/golang-lru/v2" lru "github.com/hashicorp/golang-lru/v2"
"github.com/nspcc-dev/neo-go/pkg/core/block" "github.com/nspcc-dev/neo-go/pkg/core/block"
@ -52,6 +53,10 @@ const (
defaultWaitInterval = 500 * time.Millisecond defaultWaitInterval = 500 * time.Millisecond
) )
var (
ErrNoHealthyEndpoint = errors.New("no healthy endpoint")
)
func defaultConfig() *cfg { func defaultConfig() *cfg {
return &cfg{ return &cfg{
dialTimeout: defaultDialTimeout, dialTimeout: defaultDialTimeout,
@ -80,6 +85,8 @@ func defaultConfig() *cfg {
// If desired option satisfies the default value, it can be omitted. // If desired option satisfies the default value, it can be omitted.
// If multiple options of the same config value are supplied, // If multiple options of the same config value are supplied,
// the option with the highest index in the arguments will be used. // the option with the highest index in the arguments will be used.
// If the list of endpoints provided - uses first alive.
// If there are no healthy endpoint - returns ErrNoHealthyEndpoint.
func New(ctx context.Context, key *keys.PrivateKey, opts ...Option) (*Client, error) { func New(ctx context.Context, key *keys.PrivateKey, opts ...Option) (*Client, error) {
if key == nil { if key == nil {
panic("empty private key") panic("empty private key")
@ -137,9 +144,20 @@ func New(ctx context.Context, key *keys.PrivateKey, opts ...Option) (*Client, er
return nil, fmt.Errorf("could not create RPC actor: %w", err) return nil, fmt.Errorf("could not create RPC actor: %w", err)
} }
} else { } else {
cli.client, act, err = cli.newCli(ctx, cli.endpoints.list[0].Address) var endpoint Endpoint
if err != nil { for cli.endpoints.curr, endpoint = range cli.endpoints.list {
return nil, fmt.Errorf("could not create RPC client: %w", err) cli.client, act, err = cli.newCli(ctx, endpoint.Address)
if err != nil {
cli.logger.Warn(logs.FrostFSIRCouldntCreateRPCClientForEndpoint,
zap.Error(err), zap.String("endpoint", endpoint.Address))
} else {
cli.logger.Info(logs.FrostFSIRCreatedRPCClientForEndpoint,
zap.String("endpoint", endpoint.Address))
break
}
}
if cli.client == nil {
return nil, ErrNoHealthyEndpoint
} }
} }
cli.setActor(act) cli.setActor(act)