Skip to content

Commit 59d3287

Browse files
committed
all chaos examples for k8s
1 parent c52e64f commit 59d3287

File tree

4 files changed

+128
-36
lines changed

4 files changed

+128
-36
lines changed

framework/examples/myproject/chaos/chaos_blockchain_evm_gas_test.go

Lines changed: 20 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,7 @@
11
package chaos
22

33
import (
4-
"context"
5-
"github.com/ethereum/go-ethereum/ethclient"
6-
"github.com/smartcontractkit/chainlink-testing-framework/framework"
4+
f "github.com/smartcontractkit/chainlink-testing-framework/framework"
75
"github.com/smartcontractkit/chainlink-testing-framework/framework/clclient"
86
"github.com/smartcontractkit/chainlink-testing-framework/framework/components/blockchain"
97
"github.com/smartcontractkit/chainlink-testing-framework/framework/components/fake"
@@ -15,15 +13,13 @@ import (
1513
"time"
1614
)
1715

18-
func printBlockBaseFee(t *testing.T, url string) {
19-
ec, err := ethclient.Dial(url)
20-
require.NoError(t, err)
21-
bn, err := ec.BlockNumber(context.Background())
22-
require.NoError(t, err)
23-
b, err := ec.BlockByNumber(context.Background(), big.NewInt(int64(bn)))
24-
require.NoError(t, err)
25-
t.Logf("Current block base fee: %d", b.BaseFee())
26-
}
16+
//func printBlockBaseFee(t *testing.T, rpc *rpc.RPCClient) {
17+
// bn, err := rpc.BlockNumber()
18+
// require.NoError(t, err)
19+
// b, err := rpc.GetHeaderByNumber(bn, false)
20+
// require.NoError(t, err)
21+
// f.L.Info().Uint64("BaseFee", b.BaseFee.Uint64()).Msg("Current block base fee")
22+
//}
2723

2824
type CfgGas struct {
2925
BlockchainA *blockchain.Input `toml:"blockchain_a" validate:"required"`
@@ -32,7 +28,7 @@ type CfgGas struct {
3228
}
3329

3430
func TestBlockchainGasChaos(t *testing.T) {
35-
in, err := framework.Load[CfgGas](t)
31+
in, err := f.Load[CfgGas](t)
3632
require.NoError(t, err)
3733

3834
// Can replace deployments with CRIB here
@@ -51,28 +47,31 @@ func TestBlockchainGasChaos(t *testing.T) {
5147
blockEvery := 1 * time.Second
5248
waitBetweenTests := 1 * time.Minute
5349

54-
gasControlFunc := func(t *testing.T, r *rpc.RPCClient, url string) {
50+
gasControlFunc := func(t *testing.T, r *rpc.RPCClient) {
5551
startGasPrice := big.NewInt(2e9)
5652
// ramp
5753
for i := 0; i < 10; i++ {
58-
printBlockBaseFee(t, url)
54+
err := r.PrintBlockBaseFee()
55+
require.NoError(t, err)
5956
t.Logf("Setting block base fee: %d", startGasPrice)
60-
err := r.AnvilSetNextBlockBaseFeePerGas(startGasPrice)
57+
err = r.AnvilSetNextBlockBaseFeePerGas(startGasPrice)
6158
require.NoError(t, err)
6259
startGasPrice = startGasPrice.Add(startGasPrice, big.NewInt(1e9))
6360
time.Sleep(blockEvery)
6461
}
6562
// hold
6663
for i := 0; i < 10; i++ {
67-
printBlockBaseFee(t, url)
64+
err := r.PrintBlockBaseFee()
65+
require.NoError(t, err)
6866
time.Sleep(blockEvery)
6967
t.Logf("Setting block base fee: %d", startGasPrice)
70-
err := r.AnvilSetNextBlockBaseFeePerGas(startGasPrice)
68+
err = r.AnvilSetNextBlockBaseFeePerGas(startGasPrice)
7169
require.NoError(t, err)
7270
}
7371
// release
7472
for i := 0; i < 10; i++ {
75-
printBlockBaseFee(t, url)
73+
err := r.PrintBlockBaseFee()
74+
require.NoError(t, err)
7675
time.Sleep(blockEvery)
7776
}
7877
}
@@ -82,7 +81,7 @@ func TestBlockchainGasChaos(t *testing.T) {
8281
chainURL string
8382
increase *big.Int
8483
waitBetweenTests time.Duration
85-
gasFunc func(t *testing.T, r *rpc.RPCClient, url string)
84+
gasFunc func(t *testing.T, r *rpc.RPCClient)
8685
validate func(t *testing.T, c []*clclient.ChainlinkClient)
8786
}{
8887
{
@@ -114,9 +113,8 @@ func TestBlockchainGasChaos(t *testing.T) {
114113
for _, tc := range testCases {
115114
t.Run(tc.name, func(t *testing.T) {
116115
t.Log(tc.name)
117-
printBlockBaseFee(t, tc.chainURL)
118116
r := rpc.New(tc.chainURL, nil)
119-
tc.gasFunc(t, r, tc.chainURL)
117+
tc.gasFunc(t, r)
120118
tc.validate(t, c)
121119
time.Sleep(waitBetweenTests)
122120
})

framework/examples/myproject/chaos/chaos_k8s.toml

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,9 @@ namespace = "default"
44
dashboard_uuids = ["WaspDebug"]
55
experiment_duration = "20s"
66
experiment_injection_duration = "10s"
7-
blockchain_http_urls = ["http://localhost:8545"]
7+
remove_k8s_chaos = true
8+
9+
blockchain_http_urls = ["http://localhost:8545", "http://localhost:8550"]
810
reorg_below_finality_threshold = 5
9-
reorg_above_finality_threshold = 10
11+
reorg_above_finality_threshold = 10
12+
block_every = "1s"

framework/examples/myproject/chaos/chaos_k8s_test.go

Lines changed: 55 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,7 @@ import (
66
gf "github.com/smartcontractkit/chainlink-testing-framework/framework/grafana"
77
"github.com/smartcontractkit/chainlink-testing-framework/framework/rpc"
88
"github.com/smartcontractkit/chainlink-testing-framework/havoc"
9+
"math/big"
910
"os"
1011
"testing"
1112
"time"
@@ -22,6 +23,8 @@ type K8sChaos struct {
2223
BlockchainHTTPURLs []string `toml:"blockchain_http_urls"`
2324
ReorgBelowFinalityThreshold int `toml:"reorg_below_finality_threshold"`
2425
ReorgAboveFinalityThreshold int `toml:"reorg_above_finality_threshold"`
26+
BlockEvery string `toml:"block_every"`
27+
RemoveK8sChaos bool `toml:"remove_k8s_chaos"`
2528
}
2629

2730
type CfgChaosK8s struct {
@@ -35,8 +38,41 @@ func TestK8sChaos(t *testing.T) {
3538

3639
c, err := havoc.NewChaosMeshClient()
3740
require.NoError(t, err)
38-
cr := havoc.NewNamespaceRunner(f.L, c, false)
41+
cr := havoc.NewNamespaceRunner(f.L, c, true)
3942
gc := gf.NewGrafanaClient(os.Getenv("GRAFANA_URL"), os.Getenv("GRAFANA_TOKEN"))
43+
rpc0 := rpc.New(cfg.BlockchainHTTPURLs[0], nil)
44+
rpc1 := rpc.New(cfg.BlockchainHTTPURLs[1], nil)
45+
46+
gasScheduleFunc := func(t *testing.T, r *rpc.RPCClient, url string, increase *big.Int) {
47+
startGasPrice := big.NewInt(2e9)
48+
// ramp
49+
for i := 0; i < 10; i++ {
50+
err := r.PrintBlockBaseFee()
51+
require.NoError(t, err)
52+
err = r.AnvilSetNextBlockBaseFeePerGas(startGasPrice)
53+
require.NoError(t, err)
54+
err = r.AnvilMine([]interface{}{"1"})
55+
require.NoError(t, err)
56+
time.Sleep(f.MustParseDuration(cfg.BlockEvery))
57+
startGasPrice = startGasPrice.Add(startGasPrice, increase)
58+
}
59+
// hold
60+
for i := 0; i < 10; i++ {
61+
err := r.PrintBlockBaseFee()
62+
require.NoError(t, err)
63+
err = r.AnvilSetNextBlockBaseFeePerGas(startGasPrice)
64+
require.NoError(t, err)
65+
err = r.AnvilMine([]interface{}{"1"})
66+
require.NoError(t, err)
67+
time.Sleep(f.MustParseDuration(cfg.BlockEvery))
68+
}
69+
// release
70+
for i := 0; i < 10; i++ {
71+
err := r.PrintBlockBaseFee()
72+
require.NoError(t, err)
73+
time.Sleep(f.MustParseDuration(cfg.BlockEvery))
74+
}
75+
}
4076

4177
testCases := []struct {
4278
name string
@@ -380,39 +416,49 @@ func TestK8sChaos(t *testing.T) {
380416
{
381417
name: "Reorg src chain below finality",
382418
run: func(t *testing.T) {
383-
r := rpc.New(cfg.BlockchainHTTPURLs[0], nil)
384-
err := r.GethSetHead(cfg.ReorgBelowFinalityThreshold)
419+
err := rpc0.GethSetHead(cfg.ReorgBelowFinalityThreshold)
385420
require.NoError(t, err)
386421
},
387422
validate: func(t *testing.T) {},
388423
},
389424
{
390425
name: "Reorg dst chain below finality",
391426
run: func(t *testing.T) {
392-
r := rpc.New(cfg.BlockchainHTTPURLs[1], nil)
393-
err := r.GethSetHead(cfg.ReorgBelowFinalityThreshold)
427+
err := rpc1.GethSetHead(cfg.ReorgBelowFinalityThreshold)
394428
require.NoError(t, err)
395429
},
396430
validate: func(t *testing.T) {},
397431
},
398432
{
399433
name: "Reorg src chain above finality",
400434
run: func(t *testing.T) {
401-
r := rpc.New(cfg.BlockchainHTTPURLs[0], nil)
402-
err := r.GethSetHead(cfg.ReorgAboveFinalityThreshold)
435+
err := rpc0.GethSetHead(cfg.ReorgAboveFinalityThreshold)
403436
require.NoError(t, err)
404437
},
405438
validate: func(t *testing.T) {},
406439
},
407440
{
408441
name: "Reorg dst chain above finality",
409442
run: func(t *testing.T) {
410-
r := rpc.New(cfg.BlockchainHTTPURLs[1], nil)
411-
err := r.GethSetHead(cfg.ReorgAboveFinalityThreshold)
443+
err := rpc1.GethSetHead(cfg.ReorgAboveFinalityThreshold)
412444
require.NoError(t, err)
413445
},
414446
validate: func(t *testing.T) {},
415447
},
448+
{
449+
name: "Slow spike",
450+
run: func(t *testing.T) {
451+
gasScheduleFunc(t, rpc1, cfg.BlockchainHTTPURLs[1], big.NewInt(1e9))
452+
},
453+
validate: func(t *testing.T) {},
454+
},
455+
{
456+
name: "Fast spike",
457+
run: func(t *testing.T) {
458+
gasScheduleFunc(t, rpc1, cfg.BlockchainHTTPURLs[1], big.NewInt(1e9))
459+
},
460+
validate: func(t *testing.T) {},
461+
},
416462
}
417463

418464
startsIn := f.MustParseDuration(cfg.WaitBeforeStart)

framework/rpc/rpc.go

Lines changed: 48 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,8 @@ import (
66
"encoding/hex"
77
"encoding/json"
88
"fmt"
9+
"github.com/ethereum/go-ethereum/core/types"
10+
f "github.com/smartcontractkit/chainlink-testing-framework/framework"
911
"math/big"
1012
"math/rand"
1113
"net/http"
@@ -160,9 +162,6 @@ func int64ToU128(value int64) string {
160162
// AnvilSetNextBlockBaseFeePerGas sets next block base fee per gas value
161163
// API Reference https://book.getfoundry.sh/reference/anvil/
162164
func (m *RPCClient) AnvilSetNextBlockBaseFeePerGas(gas *big.Int) error {
163-
//hexBaseFee := "0x" + strconv.FormatInt(gas, 10)
164-
//bi := big.NewInt(gas)
165-
//hexBaseFee := fmt.Sprintf("0x%x", bi)
166165
rInt := rand.Int()
167166
payload := map[string]interface{}{
168167
"jsonrpc": "2.0",
@@ -252,6 +251,37 @@ func (m *RPCClient) BlockNumber() (int64, error) {
252251
return bn, nil
253252
}
254253

254+
type BlockResponse struct {
255+
Jsonrpc string `json:"jsonrpc"`
256+
ID int `json:"id"`
257+
Result *types.Header `json:"result"`
258+
}
259+
260+
// GetHeaderByNumber retrieves block details by block number
261+
// this is purely debug method to verify the gas chaos is applied
262+
func (m *RPCClient) GetHeaderByNumber(blockNumber int64) (*types.Header, error) {
263+
rInt := rand.Int()
264+
blockNumberHex := fmt.Sprintf("0x%x", blockNumber)
265+
payload := map[string]interface{}{
266+
"jsonrpc": "2.0",
267+
"method": "eth_getBlockByNumber",
268+
"params": []interface{}{blockNumberHex, false},
269+
"id": rInt,
270+
}
271+
resp, err := m.client.R().SetBody(payload).Post(m.URL)
272+
if err != nil {
273+
return nil, errors.Wrap(err, "eth_getBlockByNumber")
274+
}
275+
var blk *BlockResponse
276+
if err := json.Unmarshal(resp.Body(), &blk); err != nil {
277+
return nil, err
278+
}
279+
if blk.Result == nil {
280+
return nil, errors.New("block not found")
281+
}
282+
return blk.Result, nil
283+
}
284+
255285
func (m *RPCClient) GethSetHead(blocksBack int) error {
256286
decimalLastBlock, err := m.BlockNumber()
257287
if err != nil {
@@ -314,3 +344,18 @@ func StartAnvil(params []string) (*AnvilContainer, error) {
314344
url := fmt.Sprintf("http://localhost:%s", mappedPort.Port())
315345
return &AnvilContainer{Container: container, URL: url}, nil
316346
}
347+
348+
// PrintBlockBaseFee prints block base fee
349+
// this is purely debug method to verify gas chaos is applied
350+
func (m *RPCClient) PrintBlockBaseFee() error {
351+
bn, err := m.BlockNumber()
352+
if err != nil {
353+
return err
354+
}
355+
b, err := m.GetHeaderByNumber(bn)
356+
if err != nil {
357+
return err
358+
}
359+
f.L.Info().Uint64("BaseFee", b.BaseFee.Uint64()).Msg("Current block")
360+
return nil
361+
}

0 commit comments

Comments
 (0)