pulsar-contracts
Version:
132 lines • 9.39 kB
JavaScript
import { Field, Poseidon, verify } from 'o1js';
import { MultisigVerifierProgram, BlockList, } from '../SettlementProof';
import { SETTLEMENT_MATRIX_SIZE, VALIDATOR_NUMBER } from '../utils/constants';
import { ProofGenerators } from '../types/proofGenerators';
import { validatorSet } from './mock';
import { GenerateSettlementPublicInput, MergeSettlementProofs, } from '../utils/generateFunctions';
import { TestUtils } from '../utils/testUtils';
import { List } from '../types/common';
import { enableLogs, log } from '../utils/loggers';
describe('SettlementProof tests', () => {
const proofsEnabled = process.env.PROOFS_ENABLED === '1';
let merkleList;
let blocks = [];
let settlementPublicInputs = [];
let settlementProofs = [];
let vk;
if (process.env.LOGS_ENABLED === '1') {
enableLogs();
}
beforeAll(async () => {
vk = (await MultisigVerifierProgram.compile({
proofsEnabled,
})).verificationKey;
merkleList = List.empty();
for (let i = 0; i < VALIDATOR_NUMBER; i++) {
const [, publicKey] = validatorSet[i];
merkleList.push(Poseidon.hash(publicKey.toFields()));
}
});
describe('Peripherals', () => {
it('should create a valid SettlementPublicInputs', () => {
blocks = TestUtils.GenerateTestBlocks(Field(1), merkleList.hash, Field(1));
const publicInput = GenerateSettlementPublicInput(blocks[0].InitialMerkleListRoot, blocks[0].InitialStateRoot, blocks[0].InitialBlockHeight, blocks[blocks.length - 1].NewMerkleListRoot, blocks[blocks.length - 1].NewStateRoot, blocks[blocks.length - 1].NewBlockHeight, [validatorSet[0][1]]);
expect(publicInput.InitialMerkleListRoot).toEqual(merkleList.hash);
expect(publicInput.InitialStateRoot).toEqual(Field.from(1));
expect(publicInput.InitialBlockHeight).toEqual(Field.from(1));
expect(publicInput.NewMerkleListRoot).toEqual(merkleList.hash);
expect(publicInput.NewStateRoot).toEqual(Field.from(SETTLEMENT_MATRIX_SIZE + 1));
expect(publicInput.NewBlockHeight).toEqual(Field.from(SETTLEMENT_MATRIX_SIZE + 1));
expect(publicInput.ProofGeneratorsList).toEqual(ProofGenerators.empty().insertAt(Field.from(0), validatorSet[0][1]));
settlementPublicInputs.push(publicInput);
});
});
describe('verifySignatures method', () => {
it('should verify signatures and create a valid SettlementProof', async () => {
const signerMatrix = TestUtils.GenerateSignaturePubKeyMatrix(blocks, Array.from({ length: SETTLEMENT_MATRIX_SIZE }, () => validatorSet));
settlementProofs.push((await MultisigVerifierProgram.verifySignatures(settlementPublicInputs[0], signerMatrix, validatorSet[0][1], BlockList.fromArray(blocks))).proof);
});
it('should verify the generated proof', async () => {
if (!proofsEnabled) {
log('Skipping proof verification');
return;
}
const isValid = await verify(settlementProofs[settlementProofs.length], vk);
expect(isValid).toBe(true);
});
it('should create another valid SettlementProof', async () => {
blocks = TestUtils.GenerateTestBlocks(settlementPublicInputs[settlementPublicInputs.length - 1]
.NewBlockHeight, settlementPublicInputs[settlementPublicInputs.length - 1]
.NewMerkleListRoot, settlementPublicInputs[settlementPublicInputs.length - 1].NewStateRoot);
const publicInput = GenerateSettlementPublicInput(settlementPublicInputs[settlementPublicInputs.length - 1]
.NewMerkleListRoot, settlementPublicInputs[settlementPublicInputs.length - 1].NewStateRoot, settlementPublicInputs[settlementPublicInputs.length - 1]
.NewBlockHeight, blocks[blocks.length - 1].NewMerkleListRoot, blocks[blocks.length - 1].NewStateRoot, blocks[blocks.length - 1].NewBlockHeight, [validatorSet[1][1]]);
settlementPublicInputs.push(publicInput);
const signerMatrix = TestUtils.GenerateSignaturePubKeyMatrix(blocks, Array.from({ length: SETTLEMENT_MATRIX_SIZE }, () => validatorSet));
settlementProofs.push((await MultisigVerifierProgram.verifySignatures(settlementPublicInputs[settlementPublicInputs.length - 1], signerMatrix, validatorSet[1][1], BlockList.fromArray(blocks))).proof);
});
it('should verify the generated proof', async () => {
if (!proofsEnabled) {
log('Skipping proof verification');
return;
}
const isValid = await verify(settlementProofs[settlementProofs.length - 1], vk);
expect(isValid).toBe(true);
});
it('should create a third valid SettlementProof', async () => {
blocks = TestUtils.GenerateTestBlocks(settlementPublicInputs[settlementPublicInputs.length - 1]
.NewBlockHeight, settlementPublicInputs[settlementPublicInputs.length - 1]
.NewMerkleListRoot, settlementPublicInputs[settlementPublicInputs.length - 1].NewStateRoot);
const publicInput = GenerateSettlementPublicInput(settlementPublicInputs[settlementPublicInputs.length - 1]
.NewMerkleListRoot, settlementPublicInputs[settlementPublicInputs.length - 1].NewStateRoot, settlementPublicInputs[settlementPublicInputs.length - 1]
.NewBlockHeight, blocks[blocks.length - 1].NewMerkleListRoot, blocks[blocks.length - 1].NewStateRoot, blocks[blocks.length - 1].NewBlockHeight, [validatorSet[2][1]]);
settlementPublicInputs.push(publicInput);
const signerMatrix = TestUtils.GenerateSignaturePubKeyMatrix(blocks, Array.from({ length: SETTLEMENT_MATRIX_SIZE }, () => validatorSet));
settlementProofs.push((await MultisigVerifierProgram.verifySignatures(settlementPublicInputs[settlementPublicInputs.length - 1], signerMatrix, validatorSet[2][1], BlockList.fromArray(blocks))).proof);
});
it('should verify the generated proof', async () => {
if (!proofsEnabled) {
log('Skipping proof verification');
return;
}
const isValid = await verify(settlementProofs[settlementProofs.length - 1], vk);
expect(isValid).toBe(true);
});
it('should create a fourth valid SettlementProof', async () => {
blocks = TestUtils.GenerateTestBlocks(settlementPublicInputs[settlementPublicInputs.length - 1]
.NewBlockHeight, settlementPublicInputs[settlementPublicInputs.length - 1]
.NewMerkleListRoot, settlementPublicInputs[settlementPublicInputs.length - 1].NewStateRoot);
const publicInput = GenerateSettlementPublicInput(settlementPublicInputs[settlementPublicInputs.length - 1]
.NewMerkleListRoot, settlementPublicInputs[settlementPublicInputs.length - 1].NewStateRoot, settlementPublicInputs[settlementPublicInputs.length - 1]
.NewBlockHeight, blocks[blocks.length - 1].NewMerkleListRoot, blocks[blocks.length - 1].NewStateRoot, blocks[blocks.length - 1].NewBlockHeight, [validatorSet[3][1]]);
settlementPublicInputs.push(publicInput);
const signerMatrix = TestUtils.GenerateSignaturePubKeyMatrix(blocks, Array.from({ length: SETTLEMENT_MATRIX_SIZE }, () => validatorSet));
settlementProofs.push((await MultisigVerifierProgram.verifySignatures(settlementPublicInputs[settlementPublicInputs.length - 1], signerMatrix, validatorSet[3][1], BlockList.fromArray(blocks))).proof);
});
it('should merge the proofs', async () => {
const mergedProof = await MergeSettlementProofs(settlementProofs);
expect(mergedProof.publicInput.NewBlockHeight).toEqual(settlementPublicInputs[settlementPublicInputs.length - 1].NewBlockHeight);
expect(mergedProof.publicInput.NewMerkleListRoot).toEqual(settlementPublicInputs[settlementPublicInputs.length - 1]
.NewMerkleListRoot);
expect(mergedProof.publicInput.NewStateRoot).toEqual(settlementPublicInputs[settlementPublicInputs.length - 1].NewStateRoot);
expect(mergedProof.publicInput.ProofGeneratorsList).toEqual(ProofGenerators.empty()
.insertAt(Field.from(0), validatorSet[0][1])
.insertAt(Field.from(1), validatorSet[1][1])
.insertAt(Field.from(2), validatorSet[2][1])
.insertAt(Field.from(3), validatorSet[3][1]));
expect(mergedProof.publicInput.InitialMerkleListRoot).toEqual(settlementPublicInputs[0].InitialMerkleListRoot);
expect(mergedProof.publicInput.InitialStateRoot).toEqual(settlementPublicInputs[0].InitialStateRoot);
expect(mergedProof.publicInput.InitialBlockHeight).toEqual(settlementPublicInputs[0].InitialBlockHeight);
settlementProofs = [mergedProof];
});
it('should verify the merged proof', async () => {
if (!proofsEnabled) {
log('Skipping proof verification');
return;
}
const isValid = await verify(settlementProofs[0], vk);
expect(isValid).toBe(true);
});
});
});
//# sourceMappingURL=SettlementProof.test.js.map