Skip to content

Commit

Permalink
Merge branch 'unstable' into nh/sim-merge-test
Browse files Browse the repository at this point in the history
  • Loading branch information
nazarhussain authored Feb 8, 2024
2 parents e4136f0 + cb99fc4 commit 6e05f37
Show file tree
Hide file tree
Showing 135 changed files with 2,340 additions and 2,157 deletions.
2 changes: 1 addition & 1 deletion .github/FUNDING.yml
Original file line number Diff line number Diff line change
@@ -1 +1 @@
custom: https://gitcoin.co/grants/6034/lodestar-typescript-eth-consensus-client-by-chains
custom: https://etherscan.io/address/0xb4da52336092db22fe8e036866d59c6488604f89
24 changes: 19 additions & 5 deletions .github/workflows/test-sim.yml
Original file line number Diff line number Diff line change
Expand Up @@ -23,9 +23,9 @@ on:
default: 40

env:
GETH_DOCKER_IMAGE: ethereum/client-go:v1.11.6
GETH_DOCKER_IMAGE: ethereum/client-go:v1.13.11
LIGHTHOUSE_DOCKER_IMAGE: sigp/lighthouse:latest-amd64-modern-dev
NETHERMIND_DOCKER_IMAGE: nethermind/nethermind:1.18.0
NETHERMIND_DOCKER_IMAGE: nethermind/nethermind:1.25.3

jobs:
tests-sim:
Expand Down Expand Up @@ -58,27 +58,41 @@ jobs:
if: steps.cache-deps.outputs.cache-hit == 'true'
# </common-build>

- name: Download required docker images before running tests
run: |
docker pull ${{env.GETH_DOCKER_IMAGE}}
docker pull ${{env.LIGHTHOUSE_DOCKER_IMAGE}}
docker pull ${{env.NETHERMIND_DOCKER_IMAGE}}
- name: Sim tests multifork
run: DEBUG='${{github.event.inputs.debug}}' yarn test:sim:multifork
working-directory: packages/cli
env:
GENESIS_DELAY_SLOTS: ${{github.event.inputs.genesisDelaySlots}}

- name: Sim tests endpoints
run: yarn test:sim:endpoints
run: DEBUG='${{github.event.inputs.debug}}' yarn test:sim:endpoints
working-directory: packages/cli
env:
GENESIS_DELAY_SLOTS: ${{github.event.inputs.genesisDelaySlots}}

- name: Sim tests deneb
run: yarn test:sim:deneb
run: DEBUG='${{github.event.inputs.debug}}' yarn test:sim:deneb
working-directory: packages/cli
env:
GENESIS_DELAY_SLOTS: ${{github.event.inputs.genesisDelaySlots}}

- name: Sim tests backup eth provider
run: yarn test:sim:backup_eth_provider
run: DEBUG='${{github.event.inputs.debug}}' yarn test:sim:backup_eth_provider
working-directory: packages/cli
env:
GENESIS_DELAY_SLOTS: ${{github.event.inputs.genesisDelaySlots}}

- name: Sim tests mixed client
run: DEBUG='${{github.event.inputs.debug}}' yarn test:sim:mixedclient
working-directory: packages/cli
env:
GENESIS_DELAY_SLOTS: ${{github.event.inputs.genesisDelaySlots}}

- name: Upload debug log test files for "packages/cli"
if: ${{ always() }}
Expand Down
15 changes: 12 additions & 3 deletions CONTRIBUTING.md
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,14 @@ To run tests:
- :test_tube: Run `yarn check-types` to check TypeScript types.
- :test_tube: Run `yarn lint` to run the linter (ESLint).

Note that to run `test:e2e`, first ensure that the environment is correctly setup by running the `run_e2e_env.sh` script.

```sh
GETH_DOCKER_IMAGE=ethereum/client-go:v1.11.6 NETHERMIND_DOCKER_IMAGE=nethermind/nethermind:1.18.0 ./scripts/run_e2e_env.sh start
```

Similarly, run `yarn download-spec-tests` before running `yarn test:spec`.

Contributing to tests:

- Test must not depend on external live resources, such that running tests for a commit must be deterministic:
Expand All @@ -53,11 +61,12 @@ If you observe following error running any of the test files that means you are

- To fix errors always focus on passing all minimal tests first without running mainnet tests.
- Spec tests often compare full expected vs actual states in JSON format.
- A single logical error can cause many spec tests to fail. To focus on a single test at a time you can use vitest's option `--bail` to stop at the first failed test
- To then run only that failed test you can run against a specific file as use vitest's filters to run only one case
- A single logical error can cause many spec tests to fail. To focus on a single test at a time you can use vitest's option `--bail 1` to stop at the first failed test
- To then run only that failed test you can run against a specific file as use vitest's filters option `-t <pattern>` to run only one case

```sh
LODESTAR_PRESET=minimal yarn vitest --run --config vitest.config.spec.ts test/spec/phase0/sanity.test.ts
cd packages/beacon-node
LODESTAR_PRESET=minimal yarn vitest --run --bail 1 --config vitest.spec.config.ts test/spec/presets/sanity.test.ts -t attester_slashing
```

## Docker
Expand Down
6 changes: 3 additions & 3 deletions Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -39,9 +39,9 @@ FROM node:20-alpine
WORKDIR /usr/app
COPY --from=build_deps /usr/app .

# NodeJS applications have a default memory limit of 2.5GB.
# This limit is bit tight for a Prater node, it is recommended to raise the limit
# NodeJS applications have a default memory limit of 4GB on most machines.
# This limit is bit tight for a Mainnet node, it is recommended to raise the limit
# since memory may spike during certain network conditions.
ENV NODE_OPTIONS=--max-old-space-size=4096
ENV NODE_OPTIONS=--max-old-space-size=8192

ENTRYPOINT ["node", "./packages/cli/bin/lodestar"]
6 changes: 3 additions & 3 deletions docker-compose.yml
Original file line number Diff line number Diff line change
Expand Up @@ -11,11 +11,11 @@ services:
- "9000:9000" # P2P port
# - "9596:9596" # REST API port
command: beacon --dataDir /data --rest --rest.address 0.0.0.0 --metrics --logFile /logs/beacon.log --logFileLevel debug --logFileDailyRotate 5
# NodeJS applications have a default memory limit of 2.5GB.
# This limit is bit tight for a Prater node, it is recommended to raise the limit
# NodeJS applications have a default memory limit of 4GB on most machines.
# This limit is bit tight for a Mainnet node, it is recommended to raise the limit
# since memory may spike during certain network conditions.
environment:
NODE_OPTIONS: --max-old-space-size=4096
NODE_OPTIONS: --max-old-space-size=8192

prometheus:
build: docker/prometheus
Expand Down
2 changes: 1 addition & 1 deletion docs/pages/getting-started/starting-a-node.md
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@ Use the `--JsonRpc.JwtSecretFile /data/jwtsecret` flag to configure the secret.
Use the `--engine-jwt-secret=<FILE>` flag to configure the secret. Use their documentation [here](https://besu.hyperledger.org/en/stable/Reference/CLI/CLI-Syntax/#engine-jwt-secret).

**For Erigon:**
Use the `--authrpc.jwtsecret` flag to configure the secret. Use their documentation [here](https://github.com/ledgerwatch/erigon#authentication-api).
Use the `--authrpc.jwtsecret` flag to configure the secret. Use their documentation [here](https://github.com/ledgerwatch/erigon?tab=readme-ov-file#beacon-chain-consensus-layer).

## Run a beacon node

Expand Down
2 changes: 1 addition & 1 deletion docs/pages/tools/flamegraphs.md
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ Next we need to update the Lodestar service by modifying the start script. We ne
```sh
node \
--perf-basic-prof \
--max-old-space-size=4096 \
--max-old-space-size=8192 \
/usr/src/lodestar/packages/cli/bin/lodestar \
beacon \
--rcConfig /home/devops/beacon/rcconfig.yml
Expand Down
3 changes: 2 additions & 1 deletion docs/pages/validator-management/vc-configuration.md
Original file line number Diff line number Diff line change
Expand Up @@ -97,13 +97,14 @@ With produceBlockV3 (enabled automatically after the Deneb hard fork), the `--bu
With Lodestar's `--builder.selection` validator options, you can select:

- `maxprofit`: Default setting for Lodestar set at `--builder.boostFactor=100`. This default setting will always choose the more profitable block. Using this option, you may customize your `--builder.boostFactor` to your preference. Examples of its usage are below.
- `executionalways`: An alias of `--builder.boostFactor=0`, which will select the local execution block, unless it fails to produce due to an error or a delay in the response from the execution client.
- `executiononly`: Beacon node will be requested to produce local execution block even if builder relays are configured. This option will always select the local execution block and will error if it couldn't produce one.
- `builderalways`: An alias of `--builder.boostFactor=18446744073709551615` (2**64 - 1), which will select the builder block, unless the builder block fails to produce. The builder block may fail to produce if it's not available, not timely or there is an indication of censorship via `shouldOverrideBuilder` from the execution payload response.
- `builderonly`: Generally used for distributed validators (DVs). No execution block production will be triggered. Therefore, if a builder block is not produced, the API will fail and _no block will be produced_.

#### Calculating builder boost factor with examples

To calculate the builder boost factor setting, you need to know what percentage you will accept a builder block for against a local execution block using the following formula: `100*100/(100+percentage)`.
To calculate the builder boost factor setting, you need to know what percentage you will accept a builder block for against a local execution block using the following formula: `100*100/(100+percentage)`. The value passed to `--builder.boostFactor` must be a valid number without decimals.

Example 1: I will only accept a builder block with 25% more value than the local execution block.
```
Expand Down
2 changes: 1 addition & 1 deletion lerna.json
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
],
"npmClient": "yarn",
"useNx": true,
"version": "1.14.0",
"version": "1.15.1",
"stream": true,
"command": {
"version": {
Expand Down
6 changes: 3 additions & 3 deletions lodestar
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
#!/usr/bin/env bash
#!/usr/bin/env sh

# Convenience script to run the lodestar binary from built source
#
# ./lodestar.sh beacon --network prater
# ./lodestar.sh beacon --network mainnet

node --trace-deprecation --max-old-space-size=4096 ./packages/cli/bin/lodestar.js "$@"
node --trace-deprecation --max-old-space-size=8192 ./packages/cli/bin/lodestar.js "$@"
1 change: 1 addition & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,7 @@
"test:browsers": "lerna run test:browsers",
"test:e2e": "lerna run test:e2e --concurrency 1",
"test:e2e:sim": "lerna run test:e2e:sim",
"download-spec-tests": "lerna run download-spec-tests",
"test:spec": "lerna run test:spec",
"test-coverage:unit": "c8 --config .c8rc.json --report-dir coverage/unit/ --all npm run test:unit",
"test-coverage:browsers": "c8 --config .c8rc.json --report-dir coverage/browsers/ --all npm run test:browsers",
Expand Down
13 changes: 6 additions & 7 deletions packages/api/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@
"bugs": {
"url": "https://github.com/ChainSafe/lodestar/issues"
},
"version": "1.14.0",
"version": "1.15.1",
"type": "module",
"exports": {
".": {
Expand Down Expand Up @@ -63,18 +63,17 @@
"coverage": "codecov -F lodestar-api",
"lint": "eslint --color --ext .ts src/ test/",
"lint:fix": "yarn run lint --fix",
"pretest": "yarn run check-types",
"test": "yarn test:unit && yarn test:e2e",
"test": "yarn test:unit",
"test:unit": "vitest --run --dir test/unit/",
"check-readme": "typescript-docs-verifier"
},
"dependencies": {
"@chainsafe/persistent-merkle-tree": "^0.6.1",
"@chainsafe/ssz": "^0.14.0",
"@lodestar/config": "^1.14.0",
"@lodestar/params": "^1.14.0",
"@lodestar/types": "^1.14.0",
"@lodestar/utils": "^1.14.0",
"@lodestar/config": "^1.15.1",
"@lodestar/params": "^1.15.1",
"@lodestar/types": "^1.15.1",
"@lodestar/utils": "^1.15.1",
"eventsource": "^2.0.2",
"qs": "^6.11.1"
},
Expand Down
20 changes: 17 additions & 3 deletions packages/api/src/beacon/routes/beacon/block.ts
Original file line number Diff line number Diff line change
Expand Up @@ -229,8 +229,12 @@ export type Api = {
* Retrieves BlobSidecar included in requested block.
* @param blockId Block identifier.
* Can be one of: "head" (canonical head in node's view), "genesis", "finalized", \<slot\>, \<hex encoded blockRoot with 0x prefix\>.
* @param indices Array of indices for blob sidecars to request for in the specified block. Returns all blob sidecars in the block if not specified.
*/
getBlobSidecars(blockId: BlockId): Promise<
getBlobSidecars(
blockId: BlockId,
indices?: number[]
): Promise<
ApiClientResponse<{
[HttpStatusCode.OK]: {executionOptimistic: ExecutionOptimistic; data: deneb.BlobSidecars};
}>
Expand Down Expand Up @@ -270,7 +274,7 @@ export type ReqTypes = {
publishBlockV2: {body: unknown; query: {broadcast_validation?: string}};
publishBlindedBlock: {body: unknown};
publishBlindedBlockV2: {body: unknown; query: {broadcast_validation?: string}};
getBlobSidecars: BlockIdOnlyReq;
getBlobSidecars: {params: {block_id: string}; query: {indices?: number[]}};
};

export function getReqSerializers(config: ChainForkConfig): ReqSerializers<Api, ReqTypes> {
Expand Down Expand Up @@ -356,7 +360,17 @@ export function getReqSerializers(config: ChainForkConfig): ReqSerializers<Api,
query: {broadcast_validation: Schema.String},
},
},
getBlobSidecars: blockIdOnlyReq,
getBlobSidecars: {
writeReq: (block_id, indices) => ({
params: {block_id: String(block_id)},
query: {indices},
}),
parseReq: ({params, query}) => [params.block_id, query.indices],
schema: {
params: {block_id: Schema.StringRequired},
query: {indices: Schema.UintArray},
},
},
};
}

Expand Down
1 change: 1 addition & 0 deletions packages/api/src/beacon/routes/validator.ts
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,7 @@ import {ExecutionOptimistic} from "./beacon/block.js";

export enum BuilderSelection {
BuilderAlways = "builderalways",
ExecutionAlways = "executionalways",
MaxProfit = "maxprofit",
/** Only activate builder flow for DVT block proposal protocols */
BuilderOnly = "builderonly",
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,9 +9,7 @@ import {testData} from "../testData/config.js";
/* eslint-disable @typescript-eslint/naming-convention */

describe("beacon / config", () => {
describe("Run generic server test", () => {
runGenericServerTest<Api, ReqTypes>(config, getClient, getRoutes, testData);
});
runGenericServerTest<Api, ReqTypes>(config, getClient, getRoutes, testData);

it("Serialize Partial Spec object", () => {
const returnTypes = getReturnTypes();
Expand Down
28 changes: 19 additions & 9 deletions packages/api/test/unit/beacon/genericServerTest/debug.test.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import {describe, it, expect, MockInstance} from "vitest";
import {describe, it, expect, MockInstance, beforeAll, afterAll} from "vitest";
import {toHexString} from "@chainsafe/ssz";
import {FastifyInstance} from "fastify";
import {ssz} from "@lodestar/types";
import {config} from "@lodestar/config/default";
import {Api, ReqTypes, routesData} from "../../../../src/beacon/routes/debug.js";
Expand All @@ -13,19 +14,28 @@ import {testData} from "../testData/debug.js";

describe(
"beacon / debug",
function () {
describe("Run generic server test", () => {
runGenericServerTest<Api, ReqTypes>(config, getClient, getRoutes, testData);
});
() => {
runGenericServerTest<Api, ReqTypes>(config, getClient, getRoutes, testData);

// Get state by SSZ

describe("getState() in SSZ format", () => {
const {baseUrl, server} = getTestServer();
const mockApi = getMockApi<Api>(routesData);
for (const route of Object.values(getRoutes(config, mockApi))) {
registerRoute(server, route);
}
let baseUrl: string;
let server: FastifyInstance;

beforeAll(async () => {
const res = getTestServer();
server = res.server;
for (const route of Object.values(getRoutes(config, mockApi))) {
registerRoute(server, route);
}
baseUrl = await res.start();
});

afterAll(async () => {
if (server !== undefined) await server.close();
});

for (const method of ["getState" as const, "getStateV2" as const]) {
it(method, async () => {
Expand Down
23 changes: 18 additions & 5 deletions packages/api/test/unit/beacon/genericServerTest/events.test.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import {describe, it, expect, beforeEach, afterEach} from "vitest";
import {describe, it, expect, beforeEach, afterEach, beforeAll, afterAll} from "vitest";
import {FastifyInstance} from "fastify";
import {sleep} from "@lodestar/utils";
import {Api, routesData, EventType, BeaconEvent} from "../../../../src/beacon/routes/events.js";
import {getClient} from "../../../../src/beacon/client/events.js";
Expand All @@ -8,11 +9,23 @@ import {getMockApi, getTestServer} from "../../../utils/utils.js";
import {eventTestData} from "../testData/events.js";

describe("beacon / events", () => {
const {baseUrl, server} = getTestServer();
const mockApi = getMockApi<Api>(routesData);
for (const route of Object.values(getRoutes(mockApi))) {
registerRoute(server, route);
}
let server: FastifyInstance;
let baseUrl: string;

beforeAll(async () => {
const res = getTestServer();
server = res.server;
for (const route of Object.values(getRoutes(mockApi))) {
registerRoute(server, route);
}

baseUrl = await res.start();
});

afterAll(async () => {
if (server !== undefined) await server.close();
});

let controller: AbortController;
beforeEach(() => {
Expand Down
6 changes: 0 additions & 6 deletions packages/api/test/unit/beacon/oapiSpec.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -130,12 +130,6 @@ const ignoredProperties: Record<string, IgnoredProperty> = {
*/
getHealth: {request: ["query.syncing_status"]},

/**
* https://github.com/ChainSafe/lodestar/issues/6185
* - must have required property 'query'
*/
getBlobSidecars: {request: ["query"]},

/*
https://github.com/ChainSafe/lodestar/issues/4638
/query - must have required property 'skip_randao_verification'
Expand Down
2 changes: 1 addition & 1 deletion packages/api/test/unit/beacon/testData/beacon.ts
Original file line number Diff line number Diff line change
Expand Up @@ -71,7 +71,7 @@ export const testData: GenericServerTestCases<Api> = {
res: undefined,
},
getBlobSidecars: {
args: ["head"],
args: ["head", [0]],
res: {executionOptimistic: true, data: ssz.deneb.BlobSidecars.defaultValue()},
},

Expand Down
Loading

0 comments on commit 6e05f37

Please sign in to comment.