mirror of
https://github.com/OffchainLabs/prysm.git
synced 2026-01-10 05:47:59 -05:00
Compare commits
8 Commits
gopkgdrive
...
el-offline
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
a4860ff055 | ||
|
|
cad38e2692 | ||
|
|
c4be13ea9c | ||
|
|
6222ebae43 | ||
|
|
ce2c914567 | ||
|
|
a1581c04f1 | ||
|
|
a04877f2b3 | ||
|
|
34a4d6e3ea |
@@ -40,6 +40,7 @@ The format is based on Keep a Changelog, and this project adheres to Semantic Ve
|
||||
- Fixed mesh size by appending `gParams.Dhi = gossipSubDhi`
|
||||
- Fix skipping partial withdrawals count.
|
||||
- recover from panics when writing the event stream [pr](https://github.com/prysmaticlabs/prysm/pull/14545)
|
||||
- `/eth/v1/node/syncing` returns `el_offline` false while the el is syncing.
|
||||
|
||||
### Security
|
||||
|
||||
|
||||
@@ -34,6 +34,7 @@ import (
|
||||
contracts "github.com/prysmaticlabs/prysm/v5/contracts/deposit"
|
||||
"github.com/prysmaticlabs/prysm/v5/encoding/bytesutil"
|
||||
"github.com/prysmaticlabs/prysm/v5/monitoring/clientstats"
|
||||
"github.com/prysmaticlabs/prysm/v5/monitoring/tracing/trace"
|
||||
"github.com/prysmaticlabs/prysm/v5/network"
|
||||
ethpb "github.com/prysmaticlabs/prysm/v5/proto/prysm/v1alpha1"
|
||||
prysmTime "github.com/prysmaticlabs/prysm/v5/time"
|
||||
@@ -41,6 +42,11 @@ import (
|
||||
"github.com/sirupsen/logrus"
|
||||
)
|
||||
|
||||
const (
|
||||
// EthSyncing request string for JSON-RPC.
|
||||
EthSyncing = "eth_syncing"
|
||||
)
|
||||
|
||||
var (
|
||||
validDepositsCount = promauto.NewCounter(prometheus.CounterOpts{
|
||||
Name: "powchain_valid_deposits_received",
|
||||
@@ -79,6 +85,7 @@ type ChainInfoFetcher interface {
|
||||
ExecutionClientConnected() bool
|
||||
ExecutionClientEndpoint() string
|
||||
ExecutionClientConnectionErr() error
|
||||
IsExecutionClientSyncing(ctx context.Context) (bool, error)
|
||||
}
|
||||
|
||||
// POWBlockFetcher defines a struct that can retrieve mainchain blocks.
|
||||
@@ -303,6 +310,20 @@ func (s *Service) updateConnectedETH1(state bool) {
|
||||
s.updateBeaconNodeStats()
|
||||
}
|
||||
|
||||
// IsExecutionClientSyncing returns true if the execution client is syncing, otherwise false.
|
||||
|
||||
func (s *Service) IsExecutionClientSyncing(ctx context.Context) (bool, error) {
|
||||
ctx, span := trace.StartSpan(ctx, "powchain.engine-api-client.IsExecutionClientSyncing")
|
||||
defer span.End()
|
||||
|
||||
var result bool
|
||||
err := s.rpcClient.CallContext(ctx, &result, EthSyncing)
|
||||
if err != nil {
|
||||
return result, handleRPCError(err)
|
||||
}
|
||||
return result, nil
|
||||
}
|
||||
|
||||
// refers to the latest eth1 block which follows the condition: eth1_timestamp +
|
||||
// SECONDS_PER_ETH1_BLOCK * ETH1_FOLLOW_DISTANCE <= current_unix_time
|
||||
func (s *Service) followedBlockHeight(ctx context.Context) (uint64, error) {
|
||||
|
||||
@@ -131,6 +131,10 @@ func (m *Chain) ExecutionClientConnectionErr() error {
|
||||
return m.CurrError
|
||||
}
|
||||
|
||||
func (m *Chain) IsExecutionClientSyncing(_ context.Context) (bool, error) {
|
||||
return false, nil
|
||||
}
|
||||
|
||||
func (m *Chain) ETH1Endpoints() []string {
|
||||
return m.Endpoints
|
||||
}
|
||||
|
||||
@@ -28,6 +28,7 @@ go_library(
|
||||
"@com_github_ethereum_go_ethereum//common/hexutil:go_default_library",
|
||||
"@com_github_libp2p_go_libp2p//core/peer:go_default_library",
|
||||
"@com_github_pkg_errors//:go_default_library",
|
||||
"@com_github_sirupsen_logrus//:go_default_library",
|
||||
"@org_golang_google_grpc//:go_default_library",
|
||||
],
|
||||
)
|
||||
|
||||
@@ -14,6 +14,7 @@ import (
|
||||
"github.com/prysmaticlabs/prysm/v5/network/httputil"
|
||||
ethpb "github.com/prysmaticlabs/prysm/v5/proto/eth/v1"
|
||||
"github.com/prysmaticlabs/prysm/v5/runtime/version"
|
||||
log "github.com/sirupsen/logrus"
|
||||
)
|
||||
|
||||
var (
|
||||
@@ -37,6 +38,18 @@ func (s *Server) GetSyncStatus(w http.ResponseWriter, r *http.Request) {
|
||||
return
|
||||
}
|
||||
|
||||
isElOnline := s.ExecutionChainInfoFetcher.ExecutionClientConnected()
|
||||
if !isElOnline {
|
||||
isSyncing, err := s.ExecutionChainInfoFetcher.IsExecutionClientSyncing(ctx)
|
||||
if err != nil {
|
||||
log.WithField("error", err.Error()).Debug("failed to get execution client sync status")
|
||||
} else if isSyncing {
|
||||
isElOnline = true
|
||||
} else {
|
||||
log.Debug("execution client is not syncing and not connected")
|
||||
}
|
||||
}
|
||||
|
||||
headSlot := s.HeadFetcher.HeadSlot()
|
||||
response := &structs.SyncStatusResponse{
|
||||
Data: &structs.SyncStatusResponseData{
|
||||
@@ -44,7 +57,7 @@ func (s *Server) GetSyncStatus(w http.ResponseWriter, r *http.Request) {
|
||||
SyncDistance: strconv.FormatUint(uint64(s.GenesisTimeFetcher.CurrentSlot()-headSlot), 10),
|
||||
IsSyncing: s.SyncChecker.Syncing(),
|
||||
IsOptimistic: isOptimistic,
|
||||
ElOffline: !s.ExecutionChainInfoFetcher.ExecutionClientConnected(),
|
||||
ElOffline: !isElOnline,
|
||||
},
|
||||
}
|
||||
httputil.WriteJson(w, response)
|
||||
|
||||
@@ -56,7 +56,6 @@ func TestSyncStatus(t *testing.T) {
|
||||
|
||||
request := httptest.NewRequest(http.MethodGet, "http://example.com", nil)
|
||||
writer := httptest.NewRecorder()
|
||||
writer.Body = &bytes.Buffer{}
|
||||
|
||||
s.GetSyncStatus(writer, request)
|
||||
assert.Equal(t, http.StatusOK, writer.Code)
|
||||
@@ -67,6 +66,26 @@ func TestSyncStatus(t *testing.T) {
|
||||
assert.Equal(t, "10", resp.Data.SyncDistance)
|
||||
assert.Equal(t, true, resp.Data.IsSyncing)
|
||||
assert.Equal(t, true, resp.Data.IsOptimistic)
|
||||
assert.Equal(t, true, resp.Data.ElOffline)
|
||||
|
||||
// if execution client is syncing return offline false
|
||||
s.ExecutionChainInfoFetcher = &testutil.MockExecutionChainInfoFetcher{Syncing: true}
|
||||
writer = httptest.NewRecorder()
|
||||
s.GetSyncStatus(writer, request)
|
||||
assert.Equal(t, http.StatusOK, writer.Code)
|
||||
resp = &structs.SyncStatusResponse{}
|
||||
require.NoError(t, json.Unmarshal(writer.Body.Bytes(), resp))
|
||||
require.NotNil(t, resp)
|
||||
assert.Equal(t, false, resp.Data.ElOffline)
|
||||
|
||||
// if execution client is connected offline should be false
|
||||
s.ExecutionChainInfoFetcher = &testutil.MockExecutionChainInfoFetcher{Connected: true}
|
||||
writer = httptest.NewRecorder()
|
||||
s.GetSyncStatus(writer, request)
|
||||
assert.Equal(t, http.StatusOK, writer.Code)
|
||||
resp = &structs.SyncStatusResponse{}
|
||||
require.NoError(t, json.Unmarshal(writer.Body.Bytes(), resp))
|
||||
require.NotNil(t, resp)
|
||||
assert.Equal(t, false, resp.Data.ElOffline)
|
||||
}
|
||||
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
package testutil
|
||||
|
||||
import (
|
||||
"context"
|
||||
"math/big"
|
||||
)
|
||||
|
||||
@@ -8,14 +9,16 @@ import (
|
||||
type MockExecutionChainInfoFetcher struct {
|
||||
CurrEndpoint string
|
||||
CurrError error
|
||||
Syncing bool
|
||||
Connected bool
|
||||
}
|
||||
|
||||
func (*MockExecutionChainInfoFetcher) GenesisExecutionChainInfo() (uint64, *big.Int) {
|
||||
return uint64(0), &big.Int{}
|
||||
}
|
||||
|
||||
func (*MockExecutionChainInfoFetcher) ExecutionClientConnected() bool {
|
||||
return true
|
||||
func (m *MockExecutionChainInfoFetcher) ExecutionClientConnected() bool {
|
||||
return m.Connected
|
||||
}
|
||||
|
||||
func (m *MockExecutionChainInfoFetcher) ExecutionClientEndpoint() string {
|
||||
@@ -25,3 +28,7 @@ func (m *MockExecutionChainInfoFetcher) ExecutionClientEndpoint() string {
|
||||
func (m *MockExecutionChainInfoFetcher) ExecutionClientConnectionErr() error {
|
||||
return m.CurrError
|
||||
}
|
||||
|
||||
func (m *MockExecutionChainInfoFetcher) IsExecutionClientSyncing(_ context.Context) (bool, error) {
|
||||
return m.Syncing, nil
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user