Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion .github/workflows/golangci-lint.yml
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ jobs:
- name: golangci-lint
uses: golangci/golangci-lint-action@v6
with:
version: v1.61.0
version: v1.62.0
- name: notify failure
if: failure() && github.ref == 'refs/heads/main'
env:
Expand Down
1 change: 1 addition & 0 deletions .golangci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -178,6 +178,7 @@ linters:
- nonamedreturns
- paralleltest
- prealloc
- recvcheck # triggers a lot of false positives
- tagliatelle
- varnamelen
- wsl
Expand Down
2 changes: 1 addition & 1 deletion .pre-commit/run_linter.sh
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
#!/usr/bin/env bash

VERSION="1.61.0"
VERSION="1.62.0"

if ! command -v golangci-lint &> /dev/null
then
Expand Down
1 change: 1 addition & 0 deletions Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,7 @@ RUN addgroup --gid "$GID" "$USER" \
&& chmod u+x /usr/local/bin/charon

WORKDIR "/opt/$USER"
RUN chown charon "/opt/$USER"
USER charon

ENTRYPOINT ["/usr/local/bin/charon"]
Expand Down
2 changes: 1 addition & 1 deletion app/obolapi/api_internal_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -63,7 +63,7 @@ func TestHttpPost(t *testing.T) {
data, err := io.ReadAll(r.Body)
require.NoError(t, err)
defer r.Body.Close()
require.Equal(t, string(data), `{"test_body_key": "test_body_value"}`)
require.JSONEq(t, string(data), `{"test_body_key": "test_body_value"}`)

w.WriteHeader(http.StatusOK)
_, err = w.Write([]byte(`"OK"`))
Expand Down
6 changes: 3 additions & 3 deletions cmd/addvalidators_internal_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -217,9 +217,9 @@ func TestRunAddValidators(t *testing.T) {
require.NoError(t, err)
require.Len(t, entries, 3)

require.True(t, strings.Contains(entries[0].Name(), "cluster-manifest"))
require.True(t, strings.Contains(entries[1].Name(), "deposit-data"))
require.True(t, strings.Contains(entries[2].Name(), "validator_keys"))
require.Contains(t, entries[0].Name(), "cluster-manifest")
require.Contains(t, entries[1].Name(), "deposit-data")
require.Contains(t, entries[2].Name(), "validator_keys")
})
}

Expand Down
16 changes: 8 additions & 8 deletions cmd/cmd.go
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,14 @@ func New() *cobra.Command {
newAlphaCmd(
newAddValidatorsCmd(runAddValidatorsSolo),
newViewClusterManifestCmd(runViewClusterManifest),
newTestCmd(
newTestAllCmd(runTestAll),
newTestPeersCmd(runTestPeers),
newTestBeaconCmd(runTestBeacon),
newTestValidatorCmd(runTestValidator),
newTestMEVCmd(runTestMEV),
newTestInfraCmd(runTestInfra),
),
),
newExitCmd(
newListActiveValidatorsCmd(runListActiveValidatorsCmd),
Expand All @@ -57,14 +65,6 @@ func New() *cobra.Command {
newFetchExitCmd(runFetchExit),
),
newUnsafeCmd(newRunCmd(app.Run, true)),
newTestCmd(
newTestAllCmd(runTestAll),
newTestPeersCmd(runTestPeers),
newTestBeaconCmd(runTestBeacon),
newTestValidatorCmd(runTestValidator),
newTestMEVCmd(runTestMEV),
newTestInfraCmd(runTestInfra),
),
)
}

Expand Down
13 changes: 13 additions & 0 deletions cmd/duration.go
Original file line number Diff line number Diff line change
Expand Up @@ -65,3 +65,16 @@ func (d *Duration) UnmarshalText(b []byte) error {

return nil
}

func RoundDuration(d Duration) Duration {
switch {
case d.Duration > time.Second:
return Duration{d.Round(10 * time.Millisecond)}
case d.Duration > time.Millisecond:
return Duration{d.Round(time.Millisecond)}
case d.Duration > time.Microsecond:
return Duration{d.Round(time.Microsecond)}
default:
return d
}
}
40 changes: 40 additions & 0 deletions cmd/duration_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -294,3 +294,43 @@ func TestDurationUnmarshalText(t *testing.T) {
})
}
}

func TestRoundDuration(t *testing.T) {
tests := []struct {
name string
in cmd.Duration
expected cmd.Duration
}{
{
name: "15.151 milliseconds",
in: cmd.Duration{15151 * time.Microsecond},
expected: cmd.Duration{15 * time.Millisecond},
},
{
name: "15.151515 milliseconds",
in: cmd.Duration{15151515 * time.Nanosecond},
expected: cmd.Duration{15 * time.Millisecond},
},
{
name: "2.344444 seconds",
in: cmd.Duration{2344444 * time.Microsecond},
expected: cmd.Duration{2340 * time.Millisecond},
},
{
name: "2.345555 seconds",
in: cmd.Duration{2345555 * time.Microsecond},
expected: cmd.Duration{2350 * time.Millisecond},
},
{
name: "15.151 microsecond",
in: cmd.Duration{15151 * time.Nanosecond},
expected: cmd.Duration{15 * time.Microsecond},
},
}
for _, test := range tests {
t.Run(test.name, func(t *testing.T) {
res := cmd.RoundDuration(test.in)
require.Equal(t, test.expected, res)
})
}
}
2 changes: 1 addition & 1 deletion cmd/test.go
Original file line number Diff line number Diff line change
Expand Up @@ -380,7 +380,7 @@ func evaluateRTT(rtt time.Duration, testRes testResult, avg time.Duration, poor
} else {
testRes.Verdict = testVerdictGood
}
testRes.Measurement = Duration{rtt}.String()
testRes.Measurement = RoundDuration(Duration{rtt}).String()

return testRes
}
Expand Down
9 changes: 1 addition & 8 deletions cmd/testbeacon.go
Original file line number Diff line number Diff line change
Expand Up @@ -830,14 +830,7 @@ func beaconSimulationTest(ctx context.Context, conf *testBeaconConfig, target st
highestRTT = sim.Max
}
}
if highestRTT.Duration > thresholdBeaconSimulationPoor {
testRes.Verdict = testVerdictPoor
} else if highestRTT.Duration > thresholdBeaconSimulationAvg {
testRes.Verdict = testVerdictAvg
} else {
testRes.Verdict = testVerdictGood
}
testRes.Measurement = highestRTT.String()
testRes = evaluateRTT(highestRTT.Duration, testRes, thresholdBeaconSimulationAvg, thresholdBeaconSimulationPoor)

log.Info(ctx, "Validators simulation finished",
z.Any("validators_count", params.TotalValidatorsCount),
Expand Down
20 changes: 8 additions & 12 deletions cmd/testinfra.go
Original file line number Diff line number Diff line change
Expand Up @@ -267,7 +267,7 @@ func infraDiskWriteSpeedTest(ctx context.Context, conf *testInfraConfig) testRes
} else {
testRes.Verdict = testVerdictGood
}
testRes.Measurement = strconv.FormatFloat(diskWriteMBs, 'f', 4, 64) + "MB/s"
testRes.Measurement = strconv.FormatFloat(diskWriteMBs, 'f', 2, 64) + "MB/s"

return testRes
}
Expand Down Expand Up @@ -370,7 +370,7 @@ func infraDiskReadSpeedTest(ctx context.Context, conf *testInfraConfig) testResu
} else {
testRes.Verdict = testVerdictGood
}
testRes.Measurement = strconv.FormatFloat(diskReadMBs, 'f', 4, 64) + "MB/s"
testRes.Measurement = strconv.FormatFloat(diskReadMBs, 'f', 2, 64) + "MB/s"

return testRes
}
Expand Down Expand Up @@ -514,16 +514,7 @@ func infraInternetLatencyTest(ctx context.Context, conf *testInfraConfig) testRe
if err != nil {
return failedTestResult(testRes, err)
}
latency := server.Latency

if latency > internetLatencyPoor {
testRes.Verdict = testVerdictPoor
} else if latency > internetLatencyAvg {
testRes.Verdict = testVerdictAvg
} else {
testRes.Verdict = testVerdictGood
}
testRes.Measurement = latency.Round(time.Microsecond).String()
testRes = evaluateRTT(server.Latency, testRes, internetLatencyAvg, internetLatencyPoor)

return testRes
}
Expand Down Expand Up @@ -612,6 +603,11 @@ func fioCommand(ctx context.Context, filename string, blocksize int, operation s
return nil, errors.Wrap(err, "exec fio command")
}

err = os.Remove(fmt.Sprintf("%v/fiotest", filename))
if err != nil {
return nil, errors.Wrap(err, "delete fio test file")
}

return cmd, nil
}

Expand Down
66 changes: 12 additions & 54 deletions cmd/testmev.go
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@ type testMEVConfig struct {
Endpoints []string
BeaconNodeEndpoint string
LoadTest bool
LoadTestBlocks uint
NumberOfPayloads uint
}

type testCaseMEV func(context.Context, *testMEVConfig, string) testResult
Expand Down Expand Up @@ -75,26 +75,29 @@ func newTestMEVCmd(runFunc func(context.Context, io.Writer, testMEVConfig) (test
return errors.New("beacon-node-endpoint should be specified when load-test is")
}

if loadTest == "false" && beaconNodeEndpoint != "" {
return errors.New("beacon-node-endpoint should be used only when load-test is")
}

return nil
})

return cmd
}

func bindTestMEVFlags(cmd *cobra.Command, config *testMEVConfig, flagsPrefix string) {
cmd.Flags().StringSliceVar(&config.Endpoints, flagsPrefix+"endpoints", nil, "[REQUIRED] Comma separated list of one or more MEV relay endpoint URLs.")
cmd.Flags().StringSliceVar(&config.Endpoints, flagsPrefix+"endpoints", nil, "Comma separated list of one or more MEV relay endpoint URLs.")
cmd.Flags().StringVar(&config.BeaconNodeEndpoint, flagsPrefix+"beacon-node-endpoint", "", "[REQUIRED] Beacon node endpoint URL used for block creation test.")
cmd.Flags().BoolVar(&config.LoadTest, flagsPrefix+"load-test", false, "Enable load test.")
cmd.Flags().UintVar(&config.LoadTestBlocks, flagsPrefix+"load-test-blocks", 3, "Amount of blocks the 'createMultipleBlocks' test will create.")
cmd.Flags().UintVar(&config.NumberOfPayloads, flagsPrefix+"number-of-payloads", 1, "Increases the accuracy of the load test by asking for multiple payloads. Increases test duration.")
mustMarkFlagRequired(cmd, flagsPrefix+"endpoints")
}

func supportedMEVTestCases() map[testCaseName]testCaseMEV {
return map[testCaseName]testCaseMEV{
{name: "Ping", order: 1}: mevPingTest,
{name: "PingMeasure", order: 2}: mevPingMeasureTest,
{name: "CreateBlock", order: 3}: mevCreateBlockTest,
{name: "CreateMultipleBlocks", order: 4}: mevCreateMultipleBlocksTest,
{name: "Ping", order: 1}: mevPingTest,
{name: "PingMeasure", order: 2}: mevPingMeasureTest,
{name: "CreateBlock", order: 3}: mevCreateBlockTest,
}
}

Expand Down Expand Up @@ -305,61 +308,16 @@ func mevCreateBlockTest(ctx context.Context, conf *testMEVConfig, target string)
return failedTestResult(testRes, err)
}

log.Info(ctx, "Starting attempts for block creation", z.Any("mev_relay", target))
rtt, err := createMEVBlock(ctx, conf, target, nextSlot, latestBlock, proposerDuties)
if err != nil {
return failedTestResult(testRes, err)
}
testRes = evaluateRTT(rtt, testRes, thresholdMEVBlockAvg, thresholdMEVBlockPoor)

return testRes
}

func mevCreateMultipleBlocksTest(ctx context.Context, conf *testMEVConfig, target string) testResult {
testRes := testResult{Name: "CreateMultipleBlocks"}

if !conf.LoadTest {
testRes.Verdict = testVerdictSkipped
return testRes
}

latestBlock, err := latestBeaconBlock(ctx, conf.BeaconNodeEndpoint)
if err != nil {
return failedTestResult(testRes, err)
}

// wait for beginning of next slot, as the block for current one might have already been proposed
latestBlockTSUnix, err := strconv.ParseInt(latestBlock.Body.ExecutionPayload.Timestamp, 10, 64)
if err != nil {
failedTestResult(testRes, err)
}
latestBlockTS := time.Unix(latestBlockTSUnix, 0)
nextBlockTS := latestBlockTS.Add(slotTime)
for time.Now().Before(nextBlockTS) && ctx.Err() == nil {
sleepWithContext(ctx, time.Millisecond)
}

latestSlot, err := strconv.ParseInt(latestBlock.Slot, 10, 64)
if err != nil {
return failedTestResult(testRes, err)
}
nextSlot := latestSlot + 1
epoch := nextSlot / slotsInEpoch
proposerDuties, err := fetchProposersForEpoch(ctx, conf, epoch)
if err != nil {
return failedTestResult(testRes, err)
}

allBlocksRTT := []time.Duration{}
log.Info(ctx, "Starting attempts for multiple block creation", z.Any("mev_relay", target), z.Any("blocks", conf.LoadTestBlocks))
log.Info(ctx, "Starting attempts for block creation", z.Any("mev_relay", target), z.Any("blocks", conf.NumberOfPayloads))
for ctx.Err() == nil {
startIteration := time.Now()
rtt, err := createMEVBlock(ctx, conf, target, nextSlot, latestBlock, proposerDuties)
if err != nil {
return failedTestResult(testRes, err)
}
allBlocksRTT = append(allBlocksRTT, rtt)
if len(allBlocksRTT) == int(conf.LoadTestBlocks) {
if len(allBlocksRTT) == int(conf.NumberOfPayloads) {
break
}
// wait for the next slot - time it took createMEVBlock - 1 sec
Expand Down
8 changes: 0 additions & 8 deletions cmd/testmev_internal_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -57,7 +57,6 @@ func TestMEVTest(t *testing.T) {
{Name: "Ping", Verdict: testVerdictOk, Measurement: "", Suggestion: "", Error: testResultError{}},
{Name: "PingMeasure", Verdict: testVerdictGood, Measurement: "", Suggestion: "", Error: testResultError{}},
{Name: "CreateBlock", Verdict: testVerdictSkipped, Measurement: "", Suggestion: "", Error: testResultError{}},
{Name: "CreateMultipleBlocks", Verdict: testVerdictSkipped, Measurement: "", Suggestion: "", Error: testResultError{}},
},
},
},
Expand All @@ -82,7 +81,6 @@ func TestMEVTest(t *testing.T) {
{Name: "Ping", Verdict: testVerdictOk, Measurement: "", Suggestion: "", Error: testResultError{}},
{Name: "PingMeasure", Verdict: testVerdictGood, Measurement: "", Suggestion: "", Error: testResultError{}},
{Name: "CreateBlock", Verdict: testVerdictFail, Measurement: "", Suggestion: "", Error: testResultError{}},
{Name: "CreateMultipleBlocks", Verdict: testVerdictFail, Measurement: "", Suggestion: "", Error: testResultError{}},
},
},
},
Expand All @@ -105,13 +103,11 @@ func TestMEVTest(t *testing.T) {
{Name: "Ping", Verdict: testVerdictFail, Measurement: "", Suggestion: "", Error: testResultError{errors.New(fmt.Sprintf(`%v: connect: connection refused`, port1))}},
{Name: "PingMeasure", Verdict: testVerdictFail, Measurement: "", Suggestion: "", Error: testResultError{errors.New(fmt.Sprintf(`%v: connect: connection refused`, port1))}},
{Name: "CreateBlock", Verdict: testVerdictSkipped, Measurement: "", Suggestion: "", Error: testResultError{}},
{Name: "CreateMultipleBlocks", Verdict: testVerdictSkipped, Measurement: "", Suggestion: "", Error: testResultError{}},
},
endpoint2: {
{Name: "Ping", Verdict: testVerdictFail, Measurement: "", Suggestion: "", Error: testResultError{errors.New(fmt.Sprintf(`%v: connect: connection refused`, port2))}},
{Name: "PingMeasure", Verdict: testVerdictFail, Measurement: "", Suggestion: "", Error: testResultError{errors.New(fmt.Sprintf(`%v: connect: connection refused`, port2))}},
{Name: "CreateBlock", Verdict: testVerdictSkipped, Measurement: "", Suggestion: "", Error: testResultError{}},
{Name: "CreateMultipleBlocks", Verdict: testVerdictSkipped, Measurement: "", Suggestion: "", Error: testResultError{}},
},
},
},
Expand Down Expand Up @@ -157,13 +153,11 @@ func TestMEVTest(t *testing.T) {
{Name: "Ping", Verdict: testVerdictFail, Measurement: "", Suggestion: "", Error: testResultError{errors.New(fmt.Sprintf(`%v: connect: connection refused`, port1))}},
{Name: "PingMeasure", Verdict: testVerdictFail, Measurement: "", Suggestion: "", Error: testResultError{errors.New(fmt.Sprintf(`%v: connect: connection refused`, port1))}},
{Name: "CreateBlock", Verdict: testVerdictSkipped, Measurement: "", Suggestion: "", Error: testResultError{}},
{Name: "CreateMultipleBlocks", Verdict: testVerdictSkipped, Measurement: "", Suggestion: "", Error: testResultError{}},
},
endpoint2: {
{Name: "Ping", Verdict: testVerdictFail, Measurement: "", Suggestion: "", Error: testResultError{errors.New(fmt.Sprintf(`%v: connect: connection refused`, port2))}},
{Name: "PingMeasure", Verdict: testVerdictFail, Measurement: "", Suggestion: "", Error: testResultError{errors.New(fmt.Sprintf(`%v: connect: connection refused`, port2))}},
{Name: "CreateBlock", Verdict: testVerdictSkipped, Measurement: "", Suggestion: "", Error: testResultError{}},
{Name: "CreateMultipleBlocks", Verdict: testVerdictSkipped, Measurement: "", Suggestion: "", Error: testResultError{}},
},
},
},
Expand Down Expand Up @@ -223,13 +217,11 @@ func TestMEVTest(t *testing.T) {
{Name: "Ping", Verdict: testVerdictFail, Measurement: "", Suggestion: "", Error: testResultError{errors.New(fmt.Sprintf(`%v: connect: connection refused`, port1))}},
{Name: "PingMeasure", Verdict: testVerdictFail, Measurement: "", Suggestion: "", Error: testResultError{errors.New(fmt.Sprintf(`%v: connect: connection refused`, port1))}},
{Name: "CreateBlock", Verdict: testVerdictSkipped, Measurement: "", Suggestion: "", Error: testResultError{}},
{Name: "CreateMultipleBlocks", Verdict: testVerdictSkipped, Measurement: "", Suggestion: "", Error: testResultError{}},
},
endpoint2: {
{Name: "Ping", Verdict: testVerdictFail, Measurement: "", Suggestion: "", Error: testResultError{errors.New(fmt.Sprintf(`%v: connect: connection refused`, port2))}},
{Name: "PingMeasure", Verdict: testVerdictFail, Measurement: "", Suggestion: "", Error: testResultError{errors.New(fmt.Sprintf(`%v: connect: connection refused`, port2))}},
{Name: "CreateBlock", Verdict: testVerdictSkipped, Measurement: "", Suggestion: "", Error: testResultError{}},
{Name: "CreateMultipleBlocks", Verdict: testVerdictSkipped, Measurement: "", Suggestion: "", Error: testResultError{}},
},
},
Score: categoryScoreC,
Expand Down
Loading