Skip to content

Commit

Permalink
test(stack/contracts-manager): add missing unit and API tests
Browse files Browse the repository at this point in the history
  • Loading branch information
0x-r4bbit committed Feb 20, 2020
1 parent fd5485e commit df40ca0
Show file tree
Hide file tree
Showing 4 changed files with 266 additions and 1 deletion.
21 changes: 20 additions & 1 deletion packages/stack/contracts-manager/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,8 @@
"lint:ts": "tslint -c tslint.json \"src/**/*.ts\"",
"qa": "npm-run-all lint _typecheck _build",
"reset": "npx rimraf dist embark-*.tgz package",
"solo": "embark-solo"
"solo": "embark-solo",
"test": "jest"
},
"eslintConfig": {
"extends": "../../../.eslintrc.json"
Expand All @@ -57,8 +58,11 @@
"web3-utils": "1.2.6"
},
"devDependencies": {
"babel-jest": "24.9.0",
"embark-solo": "^5.1.1",
"embark-testing": "^5.2.0-nightly.3",
"eslint": "6.8.0",
"jest": "24.9.0",
"npm-run-all": "4.1.5",
"rimraf": "3.0.0",
"tslint": "5.20.1",
Expand All @@ -68,5 +72,20 @@
"node": ">=10.17.0",
"npm": ">=6.11.3",
"yarn": ">=1.19.1"
},
"jest": {
"collectCoverage": true,
"testEnvironment": "node",
"testMatch": [
"**/test/**/*.js"
],
"transform": {
"\\.(js|ts)$": [
"babel-jest",
{
"rootMode": "upward"
}
]
}
}
}
4 changes: 4 additions & 0 deletions packages/stack/contracts-manager/src/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -62,6 +62,10 @@ export default class ContractsManager {
})();
}

set web3(val) {
this._web3 = val;
}

registerCommands() {
const self = this;

Expand Down
239 changes: 239 additions & 0 deletions packages/stack/contracts-manager/test/contracts-manager.spec.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,239 @@
import ContractsManager from '../src';
import Contract from '../src/contract';

import sinon from 'sinon';
import assert from 'assert';
import { fakeEmbark } from 'embark-testing';

const { embark, plugins } = fakeEmbark();

// Due to our `DAPP_PATH` dependency in `embark-utils` `dappPath()`, we need to
// ensure that this environment variable is defined.
process.env.DAPP_PATH = 'something';

describe('stack/contracts-manager', () => {

let contractsManager;

beforeEach(() => {
contractsManager = new ContractsManager(embark, { plugins });
});

afterEach(() => {
embark.teardown();
sinon.restore();
});

describe('instantiation', () => {

it('should register contracts:reset command handler', () => {
contractsManager.events.assert.commandHandlerRegistered('contracts:reset');
});


it('should register contracts:build command handler', () => {
contractsManager.events.assert.commandHandlerRegistered('contracts:build');
});

it('should register contracts:list command handler', () => {
contractsManager.events.assert.commandHandlerRegistered('contracts:list');
});

it('should register contracts:contract command handler', () => {
contractsManager.events.assert.commandHandlerRegistered('contracts:contract');
});

it('should register contracts:add command handler', () => {
contractsManager.events.assert.commandHandlerRegistered('contracts:add');
});

it('should register contracts:all command handler', () => {
contractsManager.events.assert.commandHandlerRegistered('contracts:all');
});

it('should register contracts:dependencies command handler', () => {
contractsManager.events.assert.commandHandlerRegistered('contracts:dependencies');
});

it('should register contracts:contract:byTxHash command handler', () => {
contractsManager.events.assert.commandHandlerRegistered('contracts:contract:byTxHash');
});

it('should register contracts:reset:dependencies command handler', () => {
contractsManager.events.assert.commandHandlerRegistered('contracts:reset:dependencies');
});
});

it('should add contract objects', async () => {
const testContract = {
className: 'TestContract'
};

await embark.events.request2('contracts:add', testContract);
const contract = await embark.events.request2('contracts:contract', testContract.className);
assert.equal(contract.className, testContract.className);
});

it('should return list of added contract objects', async () => {
const testContract = {
className: 'TestContract'
};

await embark.events.request2('contracts:add', testContract);
const list = await embark.events.request2('contracts:list');
assert.equal(list.length, 1);
assert.equal(list[0].className, testContract.className);
});

it('should build contracts', async (done) => {

const contractsConfig = {
contracts: {
deploy: {
TestContract: {}
}
}
};

const compiledContracts = {
TestContract: {
// `compiledContract` can't be an empty object otherwise
// contracts-manager will exclude it from processing, resulting
// in `TestContract` not being managed.
code: 'some code',
}
};

const beforeBuildAction = sinon.spy((params, cb) => cb(null, params));
embark.registerActionForEvent('contracts:build:before', beforeBuildAction);

contractsManager.buildContracts(contractsConfig, compiledContracts, (err, result) => {
assert(beforeBuildAction.calledOnce);
assert.ok(result.TestContract instanceof Contract);
done();
});
});

it('should return contracts dependencies', async () => {
const contractsConfig = {
contracts: {
deploy: {
TestContract: {
deps: ['Dep1', 'Dep2']
},
Dep1: {},
Dep2: {}
}
}
};

const compiledContracts = {
TestContract: {
code: 'foo'
},
Dep1: {},
Dep2: {}
};

const beforeBuildAction = sinon.spy((params, cb) => { cb(null, params); });
embark.registerActionForEvent('contracts:build:before', beforeBuildAction);

await embark.events.request2('contracts:build', contractsConfig, compiledContracts);
const dependencies = await embark.events.request2('contracts:dependencies');

assert(dependencies['TestContract']);
assert.equal(dependencies['TestContract'].length, 2);
});

describe('API calls', () => {

describe('GET /embark-api/contract/:contractName', () => {

const method = 'GET';
const endpoint = '/embark-api/contract/:contractName';

it(`should register ${method} ${endpoint}`, () => {
contractsManager.plugins.assert.apiCallRegistered(method, endpoint);
})

it('should return contract by name', async () => {
const TestContract = new Contract(embark.logger, {});
contractsManager.getContract = sinon.fake.returns(TestContract);

const response = await contractsManager.plugins.mock.apiCall(method, endpoint, {
params: {
className: 'TestContract'
}
});
assert(response.send.calledWith(TestContract));
});
});

describe('GET /embark-api/contracts', () => {

const method = 'GET';
const endpoint = '/embark-api/contracts';

it(`should register ${method} ${endpoint}`, () => {
contractsManager.plugins.assert.apiCallRegistered(method, endpoint);
})

it('should return list of formatted contracts', async () => {
const testContracts = [
{ className: 'TestContract' },
{ className: 'TestContract2' }
];

contractsManager.formatContracts = sinon.fake.returns(testContracts);
contractsManager.getContract = sinon.spy(name => {
return testContracts.find(contract => contract.className = name);
});

const response = await contractsManager.plugins.mock.apiCall(method, endpoint);
assert(response.send.calledWith(testContracts));
})
});

describe('POST /embark-api/contract/:contractName/deploy', () => {

const method = 'POST';
const endpoint = '/embark-api/contract/:contractName/deploy';

it(`should register ${method} ${endpoint}`, () => {
contractsManager.plugins.assert.apiCallRegistered(method, endpoint);
})

it('should deploy contract by name', async () => {
const TestContract = new Contract(embark.logger, { code: 'some code'});

function MockContract() {
return {
deploy: (args) => {
return {
estimateGas: () => Promise.resolve(100000),
send: () => Promise.resolve({ _address: 'new address' })
}
}
}
}

const Web3Mock = {
eth: {
getAccounts: () => Promise.resolve(['0xfirst']),
Contract: MockContract
}
};

contractsManager.getContract = sinon.fake.returns(TestContract);
contractsManager.web3 = Promise.resolve(Web3Mock);

const response = await contractsManager.plugins.mock.apiCall(method, endpoint, {
contractName: 'TestContract',
inputs: []
});

assert(response.send.calledWith({ result: 'new address' }));
})
});
});
});
3 changes: 3 additions & 0 deletions packages/stack/contracts-manager/tsconfig.json
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,9 @@
},
{
"path": "../../core/utils"
},
{
"path": "../../utils/testing"
}
]
}

0 comments on commit df40ca0

Please sign in to comment.