Skip to content

Commit

Permalink
Merge pull request #155 from lidofinance/feat/val-462-e2e
Browse files Browse the repository at this point in the history
e2e for duplicated keys check and invalid keys
  • Loading branch information
Amuhar authored Dec 19, 2023
2 parents 8758649 + 2e71f33 commit f290821
Show file tree
Hide file tree
Showing 8 changed files with 596 additions and 84 deletions.
2 changes: 2 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -275,6 +275,8 @@ $ yarn test:e2e
$ yarn test:cov
```

To run e2e tests, ensure the RPC_URL environment variable is set to the Goerli provider's endpoint, and generate private keys, which should be subsequently set in the WALLET_PRIVATE_KEY variable.

## Release flow

To create a new release:
Expand Down
3 changes: 3 additions & 0 deletions src/contracts/deposit/deposit.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -243,6 +243,7 @@ export class DepositService {
* The last N blocks are not stored, in order to avoid storing reorganized blocks
*/
public async updateEventsCache(): Promise<void> {
this.logger.log('try to update?');
const fetchTimeStart = performance.now();

const [currentBlock, initialCache] = await Promise.all([
Expand Down Expand Up @@ -270,6 +271,8 @@ export class DepositService {
chunkToBlock,
);

console.log('chunk?', chunkEventGroup);

updatedCachedEvents.headers.endBlock = chunkEventGroup.endBlock;
updatedCachedEvents.data = updatedCachedEvents.data.concat(
chunkEventGroup.events,
Expand Down
1 change: 1 addition & 0 deletions src/guardian/guardian.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -126,6 +126,7 @@ export class GuardianService implements OnModuleInit {

await this.depositService.handleNewBlock(blockNumber);

// TODO: e2e test 'node operator deposit frontrun' shows that it is possible to find event and not save in cache
const blockData = await this.blockGuardService.getCurrentBlockData({
blockHash,
blockNumber,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -237,7 +237,14 @@ export class StakingModuleGuardService {
intersectionsWithLidoWC: VerifiedDepositEvent[],
blockData: BlockData,
) {
const depositedPubkeys = intersectionsWithLidoWC.map(
// should not check invalid
// TODO: fix in prev PR
const validIntersections = intersectionsWithLidoWC.filter(
({ valid }) => valid,
);
if (!validIntersections.length) return [];

const depositedPubkeys = validIntersections.map(
(deposit) => deposit.pubkey,
);

Expand Down
18 changes: 9 additions & 9 deletions src/guardian/staking-module-guard/staking-module-guard.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -669,9 +669,9 @@ describe('StakingModuleGuardService', () => {
const pubkeyWithUsedKey2 = '0x3478';
const lidoWC = '0x12';
const intersectionsWithLidoWC = [
{ pubkey: pubkeyWithUsedKey1, wc: lidoWC } as any,
{ pubkey: pubkeyWithoutUsedKey, wc: lidoWC } as any,
{ pubkey: pubkeyWithUsedKey2, wc: lidoWC } as any,
{ pubkey: pubkeyWithUsedKey1, wc: lidoWC, valid: true } as any,
{ pubkey: pubkeyWithoutUsedKey, wc: lidoWC, valid: true } as any,
{ pubkey: pubkeyWithUsedKey2, wc: lidoWC, valid: true } as any,
];
// function that return list from kapi that match keys in parameter
const mockSendMessageFromGuardian = jest
Expand Down Expand Up @@ -767,9 +767,9 @@ describe('StakingModuleGuardService', () => {
const pubkey3 = '0x3478';
const lidoWC = '0x12';
const intersectionsWithLidoWC = [
{ pubkey: pubkey1, wc: lidoWC } as any,
{ pubkey: pubkey2, wc: lidoWC } as any,
{ pubkey: pubkey3, wc: lidoWC } as any,
{ pubkey: pubkey1, wc: lidoWC, valid: true } as any,
{ pubkey: pubkey2, wc: lidoWC, valid: true } as any,
{ pubkey: pubkey3, wc: lidoWC, valid: true } as any,
];
// function that return list from kapi that match keys in parameter
const mockSendMessageFromGuardian = jest
Expand Down Expand Up @@ -829,9 +829,9 @@ describe('StakingModuleGuardService', () => {
const pubkey3 = '0x3478';
const lidoWC = '0x12';
const intersectionsWithLidoWC = [
{ pubkey: pubkey1, wc: lidoWC } as any,
{ pubkey: pubkey2, wc: lidoWC } as any,
{ pubkey: pubkey3, wc: lidoWC } as any,
{ pubkey: pubkey1, wc: lidoWC, valid: true } as any,
{ pubkey: pubkey2, wc: lidoWC, valid: true } as any,
{ pubkey: pubkey3, wc: lidoWC, valid: true } as any,
];
// function that return list from kapi that match keys in parameter
const mockSendMessageFromGuardian = jest
Expand Down
2 changes: 1 addition & 1 deletion src/keys-api/keys-api.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -63,7 +63,7 @@ export class KeysApiService {

/**
*
* @param The /v1/keys/find KAPI endpoint returns a key along with its duplicates
* @param The /v1/keys/find API endpoint returns keys along with their duplicates
* @returns
*/
public async findKeysEntires(pubkeys: string[]) {
Expand Down
111 changes: 58 additions & 53 deletions test/helpers/mockKeysApi.ts
Original file line number Diff line number Diff line change
@@ -1,66 +1,52 @@
import ethers from 'ethers';
import { toHexString } from '@chainsafe/ssz';

import { KeysApiService } from '../../src/keys-api/keys-api.service';
import { NOP_REGISTRY, pk } from './../constants';
import { NOP_REGISTRY } from './../constants';
import { RegistryOperator } from 'keys-api/interfaces/RegistryOperator';
import { SRModule } from 'keys-api/interfaces';
import { ELBlockSnapshot } from 'keys-api/interfaces/ELBlockSnapshot';
import { RegistryKey } from 'keys-api/interfaces/RegistryKey';

export const mockKeysApi = (
sig: Uint8Array[],
block: ethers.providers.Block,
keysApiService: KeysApiService,
used = false,
) => {
const mockedModule = {
nonce: 6046,
type: 'grouped-onchain-v1',
id: 1,
stakingModuleAddress: NOP_REGISTRY,
moduleFee: 10,
treasuryFee: 10,
targetShare: 10,
status: 1,
name: 'NodeOperatorRegistry',
lastDepositAt: block.timestamp,
lastDepositBlock: block.number,
};
export const mockedModule = (block: ethers.providers.Block) => ({
nonce: 6046,
type: 'grouped-onchain-v1',
id: 1,
stakingModuleAddress: NOP_REGISTRY,
moduleFee: 10,
treasuryFee: 10,
targetShare: 10,
status: 1,
name: 'NodeOperatorRegistry',
lastDepositAt: block.timestamp,
lastDepositBlock: block.number,
});

const mockedMeta = {
blockNumber: block.number,
blockHash: block.hash,
timestamp: block.timestamp,
};
export const mockedMeta = (block: ethers.providers.Block) => ({
blockNumber: block.number,
blockHash: block.hash,
timestamp: block.timestamp,
});

const mockedKeys = sig.map((x) => ({
key: toHexString(pk),
depositSignature: toHexString(x),
operatorIndex: 0,
used,
export const mockedOperators: RegistryOperator[] = [
{
name: 'Dev team',
rewardAddress: '0x6D725DAe055287f913661ee0b79dE6B21F12A459',
stakingLimit: 12,
stoppedValidators: 0,
totalSigningKeys: 12,
usedSigningKeys: 10,
index: 0,
active: true,
moduleAddress: NOP_REGISTRY,
}));

const mockedOperators: RegistryOperator[] = [
{
name: 'Dev team',
rewardAddress: '0x6D725DAe055287f913661ee0b79dE6B21F12A459',
stakingLimit: 11,
stoppedValidators: 0,
totalSigningKeys: 11,
usedSigningKeys: 10,
index: 0,
active: true,
moduleAddress: NOP_REGISTRY,
},
];

jest.spyOn(keysApiService, 'getUnusedKeys').mockImplementation(async () => ({
data: mockedKeys,
meta: {
elBlockSnapshot: mockedMeta,
},
}));
},
];

export const mockedKeysApiOperators = (
keysApiService: KeysApiService,
mockedOperators: RegistryOperator[],
mockedModule: SRModule,
mockedMeta: ELBlockSnapshot,
) => {
jest
.spyOn(keysApiService, 'getOperatorListWithModule')
.mockImplementation(async () => ({
Expand All @@ -69,7 +55,26 @@ export const mockKeysApi = (
elBlockSnapshot: mockedMeta,
},
}));
};

export const mockedKeysApiUnusedKeys = (
keysApiService: KeysApiService,
mockedKeys: RegistryKey[],
mockedMeta: ELBlockSnapshot,
) => {
jest.spyOn(keysApiService, 'getUnusedKeys').mockImplementation(async () => ({
data: mockedKeys,
meta: {
elBlockSnapshot: mockedMeta,
},
}));
};

export const mockedKeysWithDuplicates = (
keysApiService: KeysApiService,
mockedKeys: RegistryKey[],
mockedMeta: ELBlockSnapshot,
) => {
jest
.spyOn(keysApiService, 'findKeysEntires')
.mockImplementation(async () => ({
Expand Down
Loading

0 comments on commit f290821

Please sign in to comment.