123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374 |
- import EVMRevert from '../../helpers/EVMRevert';
- var Message = artifacts.require('MessageHelper.sol');
- var ERC827TokenMock = artifacts.require('ERC827TokenMock.sol');
- var BigNumber = web3.BigNumber;
- var _ = require('lodash');
- var ethjsABI = require('ethjs-abi');
- require('chai')
- .use(require('chai-as-promised'))
- .use(require('chai-bignumber')(BigNumber))
- .should();
- contract('ERC827 Token', function (accounts) {
- let token;
- function findMethod (abi, name, args) {
- for (var i = 0; i < abi.length; i++) {
- const methodArgs = _.map(abi[i].inputs, 'type').join(',');
- if ((abi[i].name === name) && (methodArgs === args)) {
- return abi[i];
- }
- }
- }
- beforeEach(async function () {
- token = await ERC827TokenMock.new(accounts[0], 100);
- });
- it('should return the correct totalSupply after construction', async function () {
- let totalSupply = await token.totalSupply();
- assert.equal(totalSupply, 100);
- });
- it('should return the correct allowance amount after approval', async function () {
- let token = await ERC827TokenMock.new();
- await token.approve(accounts[1], 100);
- let allowance = await token.allowance(accounts[0], accounts[1]);
- assert.equal(allowance, 100);
- });
- it('should return correct balances after transfer', async function () {
- await token.transfer(accounts[1], 100);
- let balance0 = await token.balanceOf(accounts[0]);
- assert.equal(balance0, 0);
- let balance1 = await token.balanceOf(accounts[1]);
- assert.equal(balance1, 100);
- });
- it('should throw an error when trying to transfer more than balance', async function () {
- await token.transfer(accounts[1], 101).should.be.rejectedWith(EVMRevert);
- });
- it('should return correct balances after transfering from another account', async function () {
- await token.approve(accounts[1], 100);
- await token.transferFrom(accounts[0], accounts[2], 100, { from: accounts[1] });
- let balance0 = await token.balanceOf(accounts[0]);
- assert.equal(balance0, 0);
- let balance1 = await token.balanceOf(accounts[2]);
- assert.equal(balance1, 100);
- let balance2 = await token.balanceOf(accounts[1]);
- assert.equal(balance2, 0);
- });
- it('should throw an error when trying to transfer more than allowed', async function () {
- await token.approve(accounts[1], 99);
- await token.transferFrom(
- accounts[0], accounts[2], 100,
- { from: accounts[1] }
- ).should.be.rejectedWith(EVMRevert);
- });
- it('should throw an error when trying to transferFrom more than _from has', async function () {
- let balance0 = await token.balanceOf(accounts[0]);
- await token.approve(accounts[1], 99);
- await token.transferFrom(
- accounts[0], accounts[2], balance0 + 1,
- { from: accounts[1] }
- ).should.be.rejectedWith(EVMRevert);
- });
- describe('validating allowance updates to spender', function () {
- let preApproved;
- it('should start with zero', async function () {
- preApproved = await token.allowance(accounts[0], accounts[1]);
- assert.equal(preApproved, 0);
- });
- it('should increase by 50 then decrease by 10', async function () {
- const abiMethod = findMethod(token.abi, 'increaseApproval', 'address,uint256');
- const increaseApprovalData = ethjsABI.encodeMethod(abiMethod,
- [accounts[1], 50]
- );
- await token.sendTransaction(
- { from: accounts[0], data: increaseApprovalData }
- );
- let postIncrease = await token.allowance(accounts[0], accounts[1]);
- preApproved.plus(50).should.be.bignumber.equal(postIncrease);
- await token.decreaseApproval(accounts[1], 10);
- let postDecrease = await token.allowance(accounts[0], accounts[1]);
- postIncrease.minus(10).should.be.bignumber.equal(postDecrease);
- });
- });
- it('should increase by 50 then set to 0 when decreasing by more than 50', async function () {
- await token.approve(accounts[1], 50);
- await token.decreaseApproval(accounts[1], 60);
- let postDecrease = await token.allowance(accounts[0], accounts[1]);
- postDecrease.should.be.bignumber.equal(0);
- });
- it('should throw an error when trying to transfer to 0x0', async function () {
- await token.transfer(0x0, 100).should.be.rejectedWith(EVMRevert);
- });
- it('should throw an error when trying to transferFrom to 0x0', async function () {
- await token.approve(accounts[1], 100);
- await token.transferFrom(accounts[0], 0x0, 100, { from: accounts[1] })
- .should.be.rejectedWith(EVMRevert);
- });
- describe('Test ERC827 methods', function () {
- it(
- 'should return correct balances after transfer (with data) and show the event on receiver contract'
- , async function () {
- const message = await Message.new();
- const extraData = message.contract.showMessage.getData(
- web3.toHex(123456), 666, 'Transfer Done'
- );
- const abiMethod = findMethod(token.abi, 'transfer', 'address,uint256,bytes');
- const transferData = ethjsABI.encodeMethod(abiMethod,
- [message.contract.address, 100, extraData]
- );
- const transaction = await token.sendTransaction(
- { from: accounts[0], data: transferData }
- );
- assert.equal(2, transaction.receipt.logs.length);
- new BigNumber(100).should.be.bignumber.equal(
- await token.balanceOf(message.contract.address)
- );
- });
- it(
- 'should return correct allowance after approve (with data) and show the event on receiver contract'
- , async function () {
- const message = await Message.new();
- const extraData = message.contract.showMessage.getData(
- web3.toHex(123456), 666, 'Transfer Done'
- );
- const abiMethod = findMethod(token.abi, 'approve', 'address,uint256,bytes');
- const approveData = ethjsABI.encodeMethod(abiMethod,
- [message.contract.address, 100, extraData]
- );
- const transaction = await token.sendTransaction(
- { from: accounts[0], data: approveData }
- );
- assert.equal(2, transaction.receipt.logs.length);
- new BigNumber(100).should.be.bignumber.equal(
- await token.allowance(accounts[0], message.contract.address)
- );
- });
- it(
- 'should return correct allowance after increaseApproval (with data) and show the event on receiver contract'
- , async function () {
- const message = await Message.new();
- const extraData = message.contract.showMessage.getData(
- web3.toHex(123456), 666, 'Transfer Done'
- );
- await token.approve(message.contract.address, 10);
- new BigNumber(10).should.be.bignumber.equal(
- await token.allowance(accounts[0], message.contract.address)
- );
- const abiMethod = findMethod(token.abi, 'increaseApproval', 'address,uint256,bytes');
- const increaseApprovalData = ethjsABI.encodeMethod(abiMethod,
- [message.contract.address, 50, extraData]
- );
- const transaction = await token.sendTransaction(
- { from: accounts[0], data: increaseApprovalData }
- );
- assert.equal(2, transaction.receipt.logs.length);
- new BigNumber(60).should.be.bignumber.equal(
- await token.allowance(accounts[0], message.contract.address)
- );
- });
- it(
- 'should return correct allowance after decreaseApproval (with data) and show the event on receiver contract'
- , async function () {
- const message = await Message.new();
- await token.approve(message.contract.address, 100);
- new BigNumber(100).should.be.bignumber.equal(
- await token.allowance(accounts[0], message.contract.address)
- );
- const extraData = message.contract.showMessage.getData(
- web3.toHex(123456), 666, 'Transfer Done'
- );
- const abiMethod = findMethod(token.abi, 'decreaseApproval', 'address,uint256,bytes');
- const decreaseApprovalData = ethjsABI.encodeMethod(abiMethod,
- [message.contract.address, 60, extraData]
- );
- const transaction = await token.sendTransaction(
- { from: accounts[0], data: decreaseApprovalData }
- );
- assert.equal(2, transaction.receipt.logs.length);
- new BigNumber(40).should.be.bignumber.equal(
- await token.allowance(accounts[0], message.contract.address)
- );
- });
- it(
- 'should return correct balances after transferFrom (with data) and show the event on receiver contract'
- , async function () {
- const message = await Message.new();
- const extraData = message.contract.showMessage.getData(
- web3.toHex(123456), 666, 'Transfer Done'
- );
- await token.approve(accounts[1], 100, { from: accounts[0] });
- new BigNumber(100).should.be.bignumber.equal(
- await token.allowance(accounts[0], accounts[1])
- );
- const abiMethod = findMethod(token.abi, 'transferFrom', 'address,address,uint256,bytes');
- const transferFromData = ethjsABI.encodeMethod(abiMethod,
- [accounts[0], message.contract.address, 100, extraData]
- );
- const transaction = await token.sendTransaction(
- { from: accounts[1], data: transferFromData }
- );
- assert.equal(2, transaction.receipt.logs.length);
- new BigNumber(100).should.be.bignumber.equal(
- await token.balanceOf(message.contract.address)
- );
- });
- it('should fail inside approve (with data)', async function () {
- const message = await Message.new();
- const extraData = message.contract.fail.getData();
- const abiMethod = findMethod(token.abi, 'approve', 'address,uint256,bytes');
- const approveData = ethjsABI.encodeMethod(abiMethod,
- [message.contract.address, 10, extraData]
- );
- await token.sendTransaction(
- { from: accounts[0], data: approveData }
- ).should.be.rejectedWith(EVMRevert);
- // approval should not have gone through so allowance is still 0
- new BigNumber(0).should.be.bignumber
- .equal(await token.allowance(accounts[1], message.contract.address));
- });
- it('should fail inside transfer (with data)', async function () {
- const message = await Message.new();
- const extraData = message.contract.fail.getData();
- const abiMethod = findMethod(token.abi, 'transfer', 'address,uint256,bytes');
- const transferData = ethjsABI.encodeMethod(abiMethod,
- [message.contract.address, 10, extraData]
- );
- await token.sendTransaction(
- { from: accounts[0], data: transferData }
- ).should.be.rejectedWith(EVMRevert);
- // transfer should not have gone through, so balance is still 0
- new BigNumber(0).should.be.bignumber
- .equal(await token.balanceOf(message.contract.address));
- });
- it('should fail inside transferFrom (with data)', async function () {
- const message = await Message.new();
- const extraData = message.contract.fail.getData();
- await token.approve(accounts[1], 10, { from: accounts[2] });
- const abiMethod = findMethod(token.abi, 'transferFrom', 'address,address,uint256,bytes');
- const transferFromData = ethjsABI.encodeMethod(abiMethod,
- [accounts[2], message.contract.address, 10, extraData]
- );
- await token.sendTransaction(
- { from: accounts[1], data: transferFromData }
- ).should.be.rejectedWith(EVMRevert);
- // transferFrom should have failed so balance is still 0 but allowance is 10
- new BigNumber(10).should.be.bignumber
- .equal(await token.allowance(accounts[2], accounts[1]));
- new BigNumber(0).should.be.bignumber
- .equal(await token.balanceOf(message.contract.address));
- });
- it('should fail approve (with data) when using token contract address as receiver', async function () {
- const message = await Message.new();
- const extraData = message.contract.showMessage.getData(
- web3.toHex(123456), 666, 'Transfer Done'
- );
- const abiMethod = findMethod(token.abi, 'approve', 'address,uint256,bytes');
- const approveData = ethjsABI.encodeMethod(abiMethod,
- [token.contract.address, 100, extraData]
- );
- await token.sendTransaction(
- { from: accounts[0], data: approveData }
- ).should.be.rejectedWith(EVMRevert);
- });
- it('should fail transfer (with data) when using token contract address as receiver', async function () {
- const message = await Message.new();
- const extraData = message.contract.showMessage.getData(
- web3.toHex(123456), 666, 'Transfer Done'
- );
- const abiMethod = findMethod(token.abi, 'transfer', 'address,uint256,bytes');
- const transferData = ethjsABI.encodeMethod(abiMethod,
- [token.contract.address, 100, extraData]
- );
- await token.sendTransaction(
- { from: accounts[0], data: transferData }
- ).should.be.rejectedWith(EVMRevert);
- });
- it('should fail transferFrom (with data) when using token contract address as receiver', async function () {
- const message = await Message.new();
- const extraData = message.contract.showMessage.getData(
- web3.toHex(123456), 666, 'Transfer Done'
- );
- await token.approve(accounts[1], 1, { from: accounts[0] });
- const abiMethod = findMethod(token.abi, 'transferFrom', 'address,address,uint256,bytes');
- const transferFromData = ethjsABI.encodeMethod(abiMethod,
- [accounts[0], token.contract.address, 1, extraData]
- );
- await token.sendTransaction(
- { from: accounts[1], data: transferFromData }
- ).should.be.rejectedWith(EVMRevert);
- });
- });
- });
|