From 812b34dfe8061bc43399a9b9d8737dc1de28a5d7 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Wed, 20 May 2020 10:43:45 +0900 Subject: [PATCH 1/7] Make tests use a unique snapshot path This commit removes accidental error messages from Snapshot code. Before this commit, tests were using the same snapshot path. Since our test does not clean "db" directory and "snapshot" directory, the follower tests can read snapshots from the previous run. Since the snapshots from the previous tests were generated from unknown hash for the current test, Snapshot code was printing error messages for them. --- test/src/e2e.dynval/2/snapshot.test.ts | 17 +---------------- test/src/e2e.dynval/setup.ts | 22 ++++++++++------------ test/src/e2e/snapshot.test.ts | 12 ++++++------ test/src/helper/spawn.ts | 8 ++++++++ 4 files changed, 25 insertions(+), 34 deletions(-) diff --git a/test/src/e2e.dynval/2/snapshot.test.ts b/test/src/e2e.dynval/2/snapshot.test.ts index 54e62a3a75..445280386f 100644 --- a/test/src/e2e.dynval/2/snapshot.test.ts +++ b/test/src/e2e.dynval/2/snapshot.test.ts @@ -22,7 +22,6 @@ import * as fs from "fs"; import "mocha"; import * as path from "path"; import * as stake from "../../stakeholder"; -import * as mkdirp from "mkdirp"; import { validators } from "../../../tendermint.dynval/constants"; import { faucetAddress, faucetSecret } from "../../helper/constants"; import { PromiseExpect } from "../../helper/promise"; @@ -33,7 +32,6 @@ import { H256 } from "../../primitives/src"; chai.use(chaiAsPromised); const SNAPSHOT_CONFIG = `${__dirname}/../../../tendermint.dynval/snapshot-config.yml`; -const SNAPSHOT_PATH = `${__dirname}/../../../../snapshot/`; describe("Snapshot for Tendermint with Dynamic Validator", function() { const promiseExpect = new PromiseExpect(); @@ -50,18 +48,8 @@ describe("Snapshot for Tendermint with Dynamic Validator", function() { deposit: 10_000_000 - index // tie-breaker })), modify: () => { - mkdirp.sync(SNAPSHOT_PATH); - const snapshotPath = fs.mkdtempSync(SNAPSHOT_PATH); return { - additionalArgv: [ - "--snapshot-path", - snapshotPath, - "--config", - SNAPSHOT_CONFIG - ], - nodeAdditionalProperties: { - snapshotPath - } + additionalArgv: ["--config", SNAPSHOT_CONFIG] }; } }); @@ -94,7 +82,6 @@ describe("Snapshot for Tendermint with Dynamic Validator", function() { }); const snapshotBlock = await getSnapshotBlock(nodes[0], termMetadata1); await makeItValidator(nodes[0], freshNodeValidator); - const snapshotPath = fs.mkdtempSync(SNAPSHOT_PATH); const node = new CodeChain({ chain: `${__dirname}/../../scheme/tendermint-dynval.json`, argv: [ @@ -103,8 +90,6 @@ describe("Snapshot for Tendermint with Dynamic Validator", function() { "--password-path", `test/tendermint.dynval/${freshNodeValidator.address.value}/password.json`, "--force-sealing", - "--snapshot-path", - snapshotPath, "--config", SNAPSHOT_CONFIG, "--snapshot-hash", diff --git a/test/src/e2e.dynval/setup.ts b/test/src/e2e.dynval/setup.ts index 858a53c88c..aeb21f363f 100644 --- a/test/src/e2e.dynval/setup.ts +++ b/test/src/e2e.dynval/setup.ts @@ -44,27 +44,25 @@ interface ValidatorConfig { autoSelfNominate?: boolean; } -interface NodePropertyModifier { +interface NodePropertyModifier { additionalArgv: string[]; - nodeAdditionalProperties: T; } -export function withNodes( +export function withNodes( suite: Suite, options: { promiseExpect: PromiseExpect; validators: ValidatorConfig[]; overrideParams?: Partial; onBeforeEnable?: (nodes: CodeChain[]) => Promise; - modify?: (signer: Signer, index: number) => NodePropertyModifier; + modify?: (signer: Signer, index: number) => NodePropertyModifier; } ) { - const nodes: (CodeChain & T)[] = []; + const nodes: CodeChain[] = []; const { overrideParams = {}, modify = () => ({ - additionalArgv: [], - nodeAdditionalProperties: {} as T + additionalArgv: [] }) } = options; const initialParams = { @@ -110,13 +108,13 @@ export function findNode(nodes: CodeChain[], signer: Signer) { ); } -async function createNodes(options: { +async function createNodes(options: { promiseExpect: PromiseExpect; validators: ValidatorConfig[]; initialParams: CommonParams; onBeforeEnable?: (nodes: CodeChain[]) => Promise; - modify: (signer: Signer, index: number) => NodePropertyModifier; -}): Promise<(CodeChain & T)[]> { + modify: (signer: Signer, index: number) => NodePropertyModifier; +}): Promise { const chain = `${__dirname}/../scheme/tendermint-dynval.json`; const { promiseExpect, validators, initialParams, modify } = options; @@ -140,7 +138,7 @@ async function createNodes(options: { }); } - const nodes: (CodeChain & T)[] = []; + const nodes: CodeChain[] = []; for (let i = 0; i < validators.length; i++) { const { signer: validator } = validators[i]; const argv = [ @@ -167,7 +165,7 @@ async function createNodes(options: { argv: [...argv, ...modifier.additionalArgv], additionalKeysPath: `tendermint.dynval/${validator.address.value}/keys` }); - nodes[i] = Object.assign(node, modifier.nodeAdditionalProperties); + nodes[i] = node; nodes[i].signer = validator; } let bootstrapFailed = false; diff --git a/test/src/e2e/snapshot.test.ts b/test/src/e2e/snapshot.test.ts index 0127529d9d..a52f9d4db6 100644 --- a/test/src/e2e/snapshot.test.ts +++ b/test/src/e2e/snapshot.test.ts @@ -22,14 +22,10 @@ import * as path from "path"; import { aliceAddress } from "../helper/constants"; import CodeChain from "../helper/spawn"; -const SNAPSHOT_PATH = `${__dirname}/../../../snapshot/`; - describe("Snapshot", async function() { let node: CodeChain; before(async function() { - node = new CodeChain({ - argv: ["--snapshot-path", SNAPSHOT_PATH] - }); + node = new CodeChain(); await node.start(); }); @@ -50,7 +46,11 @@ describe("Snapshot", async function() { blockHash }))!.stateRoot; expect( - path.join(SNAPSHOT_PATH, blockHash.substr(2), stateRoot.substr(2)) + path.join( + node.snapshotPath, + blockHash.substr(2), + stateRoot.substr(2) + ) ).to.satisfies(fs.existsSync); }); diff --git a/test/src/helper/spawn.ts b/test/src/helper/spawn.ts index b58a752c5f..353034f8ba 100644 --- a/test/src/helper/spawn.ts +++ b/test/src/helper/spawn.ts @@ -72,6 +72,7 @@ export default class CodeChain { private readonly _testFramework: SDK; private readonly _localKeyStorePath: string; private readonly _dbPath: string; + private readonly _snapshotPath: string; private readonly _ipcPath: string; private readonly _keysPath: string; private readonly _logFile: string; @@ -111,6 +112,9 @@ export default class CodeChain { public get dbPath(): string { return this._dbPath; } + public get snapshotPath(): string { + return this._snapshotPath; + } public get ipcPath(): string { return this._ipcPath; } @@ -164,7 +168,9 @@ export default class CodeChain { mkdirp.sync(`${projectRoot}/db/`); mkdirp.sync(`${projectRoot}/keys/`); mkdirp.sync(`${projectRoot}/test/log/`); + mkdirp.sync(`${projectRoot}/snapshot/`); this._dbPath = mkdtempSync(`${projectRoot}/db/`); + this._snapshotPath = mkdtempSync(`${projectRoot}/db/`); this._ipcPath = `/tmp/jsonrpc.${new Date() .toISOString() .replace(/[-:.]/g, "_")}.${this.id}.ipc`; @@ -244,6 +250,8 @@ export default class CodeChain { this.chain, "--db-path", this.dbPath, + "--snapshot-path", + this.snapshotPath, "--keys-path", this.keysPath, "--no-ws", From c97ae3db29bf24bfd673678b3c59d34a3feedf9c Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Wed, 20 May 2020 11:08:07 +0900 Subject: [PATCH 2/7] Add @types/bn.js Add @types/bn.js to dev dependency to remove the error from typescript compile. When we run `yarn tsc -p . --noEmit`, it failed since we can't find @types/bn.js. We are not using directly @types/bn.js, but rlp library depends on it. --- test/package.json | 1 + test/yarn.lock | 7 +++++++ 2 files changed, 8 insertions(+) diff --git a/test/package.json b/test/package.json index fc36a4e4b4..ad17bbb877 100644 --- a/test/package.json +++ b/test/package.json @@ -29,6 +29,7 @@ "fmt": "tslint -p . --fix && prettier 'src/**/*.{ts, json}' --write" }, "devDependencies": { + "@types/bn.js": "^4.11.6", "@types/chai": "^4.2.5", "@types/chai-as-promised": "^7.1.2", "@types/crypto-js": "^3.1.44", diff --git a/test/yarn.lock b/test/yarn.lock index 8ca2337eea..b24d6769ac 100644 --- a/test/yarn.lock +++ b/test/yarn.lock @@ -23,6 +23,13 @@ resolved "https://registry.yarnpkg.com/@types/bluebird/-/bluebird-3.5.30.tgz#ee034a0eeea8b84ed868b1aa60d690b08a6cfbc5" integrity sha512-8LhzvcjIoqoi1TghEkRMkbbmM+jhHnBokPGkJWjclMK+Ks0MxEBow3/p2/iFTZ+OIbJHQDSfpgdZEb+af3gfVw== +"@types/bn.js@^4.11.6": + version "4.11.6" + resolved "https://registry.yarnpkg.com/@types/bn.js/-/bn.js-4.11.6.tgz#c306c70d9358aaea33cd4eda092a742b9505967c" + integrity sha512-pqr857jrp2kPuO9uRjZ3PwnJTjoQy+fcdxvBTvHm6dkmEL9q+hDD/2j/0ELOBPtPnS8LjCX0gI9nbl8lVkadpg== + dependencies: + "@types/node" "*" + "@types/caseless@*": version "0.12.2" resolved "https://registry.yarnpkg.com/@types/caseless/-/caseless-0.12.2.tgz#f65d3d6389e01eeb458bd54dc8f52b95a9463bc8" From aa2686b133cf74b1c356edf7529c6eec394389fb Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Wed, 20 May 2020 11:11:57 +0900 Subject: [PATCH 3/7] Remove deprecated comment on SDK Since we removed RPC from SDK, we are not receiving server parameter in SDK constructor. --- test/src/sdk/index.ts | 1 - 1 file changed, 1 deletion(-) diff --git a/test/src/sdk/index.ts b/test/src/sdk/index.ts index b58c5e5959..e65816447d 100644 --- a/test/src/sdk/index.ts +++ b/test/src/sdk/index.ts @@ -39,7 +39,6 @@ class SDK { private _networkId: string; /** - * @param params.server HTTP RPC server address * @param params.keyStoreType Specify the type of the keystore. The default value is "local". It creates keystore.db file on the working directory. * @param params.networkId The network id of CodeChain. The default value is "tc" (testnet) */ From 0c9ef95041cffcb7b6b44367834e64b94550df76 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Wed, 20 May 2020 11:27:57 +0900 Subject: [PATCH 4/7] Fix mock example code --- test/src/helper/mock/example/send-tx.ts | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) diff --git a/test/src/helper/mock/example/send-tx.ts b/test/src/helper/mock/example/send-tx.ts index bb761433b3..02dbcf7730 100644 --- a/test/src/helper/mock/example/send-tx.ts +++ b/test/src/helper/mock/example/send-tx.ts @@ -1,5 +1,5 @@ import { Mock } from ".."; -import * as SDK from "../../../sdk"; +import { SDK } from "../../../sdk"; async function sendTransaction() { const mock = new Mock("0.0.0.0", 3485, "tc"); @@ -7,20 +7,19 @@ async function sendTransaction() { await mock.establish(); const sdk = new SDK({ - server: process.env.CODECHAIN_RPC_HTTP || "http://localhost:8080", networkId: process.env.CODECHAIN_NETWORK_ID || "tc" }); const ACCOUNT_SECRET = process.env.ACCOUNT_SECRET || "9af28f6fd6a1170dbee2cb8c34abab0408e6d811d212cdcde23f72473eb0d97ad7a6d266837c1c591383b90d835068b9ed58dd3bcebd6e285911f58e40ce413c"; const unsigned = sdk.core.createPayTransaction({ - recipient: "tccqruq09sfgax77nj4gukjcuq69uzeyv0jcs7vzngg", - amount: 10000 + recipient: "fys3db1kOrI_rXyaTx9U2_RP-SlNK1q0LRXxYeQGBI1av35drZQtc0", + quantity: 10000 }); const signed = unsigned.sign({ secret: ACCOUNT_SECRET, fee: 10, - nonce: 0 + seq: 0 }); await mock.sendEncodedTransaction([signed.toEncodeObject()]); From 51eaaebe6b90dbb1342634039f56604a8f24ce04 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Wed, 20 May 2020 11:28:59 +0900 Subject: [PATCH 5/7] Make typescript check type errors in test files --- test/package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/package.json b/test/package.json index ad17bbb877..c40e5ca3f2 100644 --- a/test/package.json +++ b/test/package.json @@ -25,7 +25,7 @@ "test-mock": "mocha -r ts-node/register --timeout 5000 \"src/helper/mock/**/*.test.ts\"", "tendermint-test-local": "cargo build --release && NODE_ENV=production ts-node src/tendermint.test/local.ts", "tendermint-test-remote": "NODE_ENV=production ts-node src/tendermint.test/remote.ts", - "lint": "tslint -p . && prettier 'src/**/*.{ts, json}' -l", + "lint": "tsc -p . --noEmit && tslint -p . && prettier 'src/**/*.{ts, json}' -l", "fmt": "tslint -p . --fix && prettier 'src/**/*.{ts, json}' --write" }, "devDependencies": { From c3878e478e3889a45f7a6e5b4e9c4bdaf13f3f2f Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Wed, 20 May 2020 12:03:17 +0900 Subject: [PATCH 6/7] Make Foundry makes blocks slowly if RUN_ON_TEST is set This will make Foundry in tests not to increase view to high. Before this commit, some tests (for example dv.nomination.test.ts) sometimes creates a block with a very high view like 9. It was because blocks were created so fast and the timestamp of a block is too future for Foundry. --- core/src/miner/miner.rs | 10 +++++++++- test/src/e2e/staking.test.ts | 2 +- test/src/helper/spawn.ts | 1 + 3 files changed, 11 insertions(+), 2 deletions(-) diff --git a/core/src/miner/miner.rs b/core/src/miner/miner.rs index 15d8833bc0..a49da6ef47 100644 --- a/core/src/miner/miner.rs +++ b/core/src/miner/miner.rs @@ -43,7 +43,7 @@ use std::iter::FromIterator; use std::ops::Range; use std::sync::atomic::{AtomicBool, Ordering}; use std::sync::Arc; -use std::time::{Duration, Instant}; +use std::time::{Duration, Instant, SystemTime, UNIX_EPOCH}; /// Configures the behaviour of the miner. #[derive(Debug, PartialEq)] @@ -516,6 +516,14 @@ impl MinerService for Miner { } }; + if std::env::var("RUN_ON_TEST").is_ok() { + let now = SystemTime::now().duration_since(UNIX_EPOCH).expect("There is no time machine.").as_secs(); + if block.header().timestamp() > now { + let delta = block.header().timestamp() - now; + std::thread::sleep(std::time::Duration::from_secs(delta)); + } + } + if self.engine.seals_internally() { ctrace!(MINER, "update_sealing: engine indicates internal sealing"); if self.import_block_internally(chain, block) { diff --git a/test/src/e2e/staking.test.ts b/test/src/e2e/staking.test.ts index d86bc4356e..cc7602d84f 100644 --- a/test/src/e2e/staking.test.ts +++ b/test/src/e2e/staking.test.ts @@ -861,7 +861,7 @@ describe("Staking", function() { address: validator1Address.toString() }))!; expect(validator1Balance).to.be.deep.equal(oldValidator1Balance); - }); + }).timeout(60_000); afterEach(async function() { if (this.currentTest!.state === "failed") { diff --git a/test/src/helper/spawn.ts b/test/src/helper/spawn.ts index 353034f8ba..2d9eb9082d 100644 --- a/test/src/helper/spawn.ts +++ b/test/src/helper/spawn.ts @@ -265,6 +265,7 @@ export default class CodeChain { { cwd: projectRoot, env: { + RUN_ON_TEST: "1", ...process.env, ...this.env } From 65f05a2e1d405541d165c74c6eef8457ef895704 Mon Sep 17 00:00:00 2001 From: Park Juhyung Date: Wed, 20 May 2020 14:05:08 +0900 Subject: [PATCH 7/7] Fix typo in snapshot.test.ts --- test/src/e2e/snapshot.test.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/src/e2e/snapshot.test.ts b/test/src/e2e/snapshot.test.ts index a52f9d4db6..b6467ae2e8 100644 --- a/test/src/e2e/snapshot.test.ts +++ b/test/src/e2e/snapshot.test.ts @@ -29,7 +29,7 @@ describe("Snapshot", async function() { await node.start(); }); - it("can make a snapshot when it is requsted with devel rpc", async function() { + it("can make a snapshot when it is requested with devel rpc", async function() { const pay = await node.sendPayTx({ quantity: 100, recipient: aliceAddress