@@ -5,12 +5,15 @@ import (
55 "net/http"
66 "net/http/httptest"
77 "testing"
8+ "time"
89
910 "github.com/evstack/ev-node/pkg/config"
1011 "github.com/evstack/ev-node/test/mocks"
12+ "github.com/evstack/ev-node/types"
1113 "github.com/rs/zerolog"
1214 "github.com/stretchr/testify/assert"
1315 "github.com/stretchr/testify/mock"
16+ "github.com/stretchr/testify/require"
1417)
1518
1619func TestRegisterCustomHTTPEndpoints (t * testing.T ) {
@@ -38,3 +41,95 @@ func TestRegisterCustomHTTPEndpoints(t *testing.T) {
3841
3942 mockStore .AssertExpectations (t )
4043}
44+
45+ func TestHealthReady_aggregatorBlockDelay (t * testing.T ) {
46+ ctx := t .Context ()
47+ logger := zerolog .Nop ()
48+
49+ type spec struct {
50+ name string
51+ lazy bool
52+ blockTime time.Duration
53+ lazyInterval time.Duration
54+ delay time.Duration
55+ expStatusCode int
56+ expBody string
57+ }
58+
59+ specs := map [string ]spec {
60+ "aggregator within non-lazy threshold" : {
61+ lazy : false ,
62+ blockTime : 200 * time .Millisecond ,
63+ lazyInterval : 0 ,
64+ delay : 800 * time .Millisecond , // 5x blockTime = 1s, so 0.8s is OK
65+ expStatusCode : http .StatusOK ,
66+ expBody : "READY\n " ,
67+ },
68+ "aggregator exceeds non-lazy threshold" : {
69+ lazy : false ,
70+ blockTime : 200 * time .Millisecond ,
71+ lazyInterval : 0 ,
72+ delay : 1500 * time .Millisecond , // > 1s threshold
73+ expStatusCode : http .StatusServiceUnavailable ,
74+ expBody : "UNREADY: aggregator not producing blocks at expected rate\n " ,
75+ },
76+ "aggregator within lazy threshold" : {
77+ lazy : true ,
78+ blockTime : 0 ,
79+ lazyInterval : 300 * time .Millisecond ,
80+ delay : 500 * time .Millisecond , // 2x lazyInterval = 600ms, so 0.5s is OK
81+ expStatusCode : http .StatusOK ,
82+ expBody : "READY\n " ,
83+ },
84+ "aggregator exceeds lazy threshold" : {
85+ lazy : true ,
86+ blockTime : 0 ,
87+ lazyInterval : 300 * time .Millisecond ,
88+ delay : 800 * time .Millisecond , // > 600ms threshold
89+ expStatusCode : http .StatusServiceUnavailable ,
90+ expBody : "UNREADY: aggregator not producing blocks at expected rate\n " ,
91+ },
92+ }
93+
94+ for name , tc := range specs {
95+ t .Run (name , func (t * testing.T ) {
96+ mux := http .NewServeMux ()
97+
98+ cfg := config .DefaultConfig ()
99+ cfg .Node .Aggregator = true
100+ if tc .blockTime > 0 {
101+ cfg .Node .BlockTime = config.DurationWrapper {Duration : tc .blockTime }
102+ }
103+ cfg .Node .LazyMode = tc .lazy
104+ if tc .lazy {
105+ cfg .Node .LazyBlockInterval = config.DurationWrapper {Duration : tc .lazyInterval }
106+ }
107+
108+ mockStore := mocks .NewMockStore (t )
109+ state := types.State {
110+ LastBlockHeight : 10 ,
111+ LastBlockTime : time .Now ().Add (- tc .delay ),
112+ }
113+ mockStore .On ("GetState" , mock .Anything ).Return (state , nil )
114+
115+ bestKnownHeightProvider := func () uint64 { return state .LastBlockHeight }
116+
117+ RegisterCustomHTTPEndpoints (mux , mockStore , nil , cfg , bestKnownHeightProvider , logger )
118+
119+ ts := httptest .NewServer (mux )
120+ t .Cleanup (ts .Close )
121+
122+ req , err := http .NewRequestWithContext (ctx , http .MethodGet , ts .URL + "/health/ready" , nil )
123+ require .NoError (t , err )
124+ resp , err := http .DefaultClient .Do (req )
125+ require .NoError (t , err )
126+ t .Cleanup (func () { _ = resp .Body .Close () })
127+
128+ body , err := io .ReadAll (resp .Body )
129+ require .NoError (t , err )
130+
131+ assert .Equal (t , tc .expStatusCode , resp .StatusCode )
132+ assert .Equal (t , tc .expBody , string (body ))
133+ })
134+ }
135+ }
0 commit comments