Child -> Cloned

This commit is contained in:
Jordi Baylina 2016-11-11 18:43:07 +01:00
parent 3471fed908
commit 3a9ef00cc5
2 changed files with 51 additions and 49 deletions

View File

@ -20,7 +20,7 @@ pragma solidity ^0.4.4;
/// @title MiniMeToken Contract
/// @author Jordi Baylina
/// @dev This token contract's goal is to make it easy to clone this token to
/// spawn child tokens using the token distribution at a given block.
/// spawn cloned tokens using the token distribution at a given block.
/// @dev It is ERC20 compliant, but still needs to under go further testing.
@ -40,7 +40,9 @@ contract Controlled {
}
}
contract TokenCreation {
// The controller should implement this interface if wants to receive the ether
// sent directly to the token contract.
contract Controller {
function proxyPayment(address _owner) payable returns(bool);
}
@ -53,7 +55,7 @@ contract MiniMeToken is Controlled {
/// @dev `Checkpoint` is the structure that attaches a block number to the a
/// given token attribute
/// given value
struct Checkpoint {
// `fromBlock` is the block number that the value was generated from
@ -323,37 +325,37 @@ contract MiniMeToken is Controlled {
// Clone Token Method
////////////////
/// @notice Creates a new child token with the initial distribution being
/// @notice Creates a new cloned token with the initial distribution being
/// this token at `_snapshotBlock`
/// @param _childTokenName Name of the child token
/// @param _childDecimalUnits Units of the child token
/// @param _childTokenSymbol Symbol of the child token
/// @param _clonedTokenName Name of the cloned token
/// @param _clonedDecimalUnits Units of the cloned token
/// @param _clonedTokenSymbol Symbol of the cloned token
/// @param _snapshotBlock Block when the distribution of the parent token is
/// copied to set the initial distribution of the new child token;
/// copied to set the initial distribution of the new cloned token;
/// if the block is higher than the actual block, the current block is used
/// @param _isConstant True if transfers are not allowed in the child token
/// @param _isConstant True if transfers are not allowed in the cloned token
/// if the block is higher than the actual block, the current block is used
/// @return The address of the new MiniMeToken Contract
function createChildToken(
string _childTokenName,
uint8 _childDecimalUnits,
string _childTokenSymbol,
function createClonedToken(
string _clonedTokenName,
uint8 _clonedDecimalUnits,
string _clonedTokenSymbol,
uint _snapshotBlock,
bool _isConstant
) returns(address) {
if (_snapshotBlock > block.number) _snapshotBlock = block.number;
MiniMeToken childToken = tokenFactory.createChildToken(
MiniMeToken clonedToken = tokenFactory.createClonedToken(
this,
_snapshotBlock,
_childTokenName,
_childDecimalUnits,
_childTokenSymbol,
_clonedTokenName,
_clonedDecimalUnits,
_clonedTokenSymbol,
_isConstant
);
// An event to make the token easy to find on the blockchain
NewChildToken(address(childToken), _snapshotBlock);
return address(childToken);
NewClonedToken(address(clonedToken), _snapshotBlock);
return address(clonedToken);
}
////////////////
@ -446,7 +448,7 @@ contract MiniMeToken is Controlled {
/// contract) using the `proxyPayment` method.
function () payable {
if (controller == 0) throw;
if (! TokenCreation(controller).proxyPayment.value(msg.value)(msg.sender)) {
if (! Controller(controller).proxyPayment.value(msg.value)(msg.sender)) {
throw;
}
}
@ -456,7 +458,7 @@ contract MiniMeToken is Controlled {
// Events
////////////////
event Transfer(address indexed _from, address indexed _to, uint256 _amount);
event NewChildToken(address indexed _childToken, uint _snapshotBlock);
event NewClonedToken(address indexed _clonedToken, uint _snapshotBlock);
event Approval(
address indexed _owner,
address indexed _spender,
@ -470,11 +472,11 @@ contract MiniMeToken is Controlled {
// MiniMeTokenFactory
////////////////
// This contract is used to generate child contracts from a contract.
// This contract is used to generate cloned contracts from a contract.
// In solidity this is the way to create a contract from a contract of the same
// class
contract MiniMeTokenFactory {
function createChildToken(
function createClonedToken(
address _parentToken,
uint _snapshotBlock,
string _tokenName,

View File

@ -21,7 +21,7 @@ var verbose = false;
// b[2] -> 0, 8, 2, 0
// b[3] -> 0, 9, 1, 0
// b[4] -> 0, 6, 1, 0
// Child token
// Cloned token
// b[5] -> 0, 6, 1, 0
// b[6] -> 0, 2, 5. 0
@ -29,7 +29,7 @@ var verbose = false;
describe('MiniMeToken test', function(){
var miniMeToken;
var miniMeTokenChild;
var miniMeTokenCloned;
var b = [];
before(function(done) {
@ -310,12 +310,12 @@ describe('MiniMeToken test', function(){
});
});
it('Should Create the child token', function(done) {
it('Should Create the cloned token', function(done) {
this.timeout(200000000);
async.series([
function(cb) {
miniMeToken.createChildToken(
"Child Token 1",
miniMeToken.createClonedToken(
"Cloned Token 1",
18,
"MMTc",
Number.MAX_SAFE_INTEGER,
@ -327,10 +327,10 @@ describe('MiniMeToken test', function(){
function(err, txHash) {
assert.ifError(err);
ethConnector.web3.eth.getTransactionReceipt(txHash, function(err, res) {
var childTokenAddr = ethConnector.web3.toBigNumber(res.logs[0].topics[1]).toString(16);
while (childTokenAddr.length < 40) childTokenAddr = '0' + childTokenAddr;
childTokenAddr = '0x' + childTokenAddr;
miniMeTokenChild = ethConnector.web3.eth.contract( miniMeTokenHelper.miniMeTokenAbi).at(childTokenAddr);
var clonedTokenAddr = ethConnector.web3.toBigNumber(res.logs[0].topics[1]).toString(16);
while (clonedTokenAddr.length < 40) clonedTokenAddr = '0' + clonedTokenAddr;
clonedTokenAddr = '0x' + clonedTokenAddr;
miniMeTokenCloned = ethConnector.web3.eth.contract( miniMeTokenHelper.miniMeTokenAbi).at(clonedTokenAddr);
cb();
});
});
@ -344,42 +344,42 @@ describe('MiniMeToken test', function(){
});
},
function(cb) {
miniMeTokenChild.parentToken(function(err, _parentAddress) {
miniMeTokenCloned.parentToken(function(err, _parentAddress) {
assert.ifError(err);
assert.equal(_parentAddress, miniMeToken.address);
cb();
});
},
function(cb) {
miniMeTokenChild.parentSnapShotBlock(function(err, _parentSnapshotBlock) {
miniMeTokenCloned.parentSnapShotBlock(function(err, _parentSnapshotBlock) {
assert.ifError(err);
assert.equal(_parentSnapshotBlock, b[5]);
cb();
});
},
function(cb) {
miniMeTokenChild.totalSupply(function(err, _balance) {
miniMeTokenCloned.totalSupply(function(err, _balance) {
assert.ifError(err);
assert.equal(ethConnector.web3.fromWei(_balance), 7);
cb();
});
},
function(cb) {
miniMeTokenChild.balanceOf(ethConnector.accounts[1], function(err, _balance) {
miniMeTokenCloned.balanceOf(ethConnector.accounts[1], function(err, _balance) {
assert.ifError(err);
assert.equal(ethConnector.web3.fromWei(_balance), 6);
cb();
});
},
function(cb) {
miniMeTokenChild.totalSupplyAt(b[4], function(err, _balance) {
miniMeTokenCloned.totalSupplyAt(b[4], function(err, _balance) {
assert.ifError(err);
assert.equal(ethConnector.web3.fromWei(_balance), 0);
cb();
});
},
function(cb) {
miniMeTokenChild.balanceOfAt(ethConnector.accounts[2], b[4], function(err, _balance) {
miniMeTokenCloned.balanceOfAt(ethConnector.accounts[2], b[4], function(err, _balance) {
assert.ifError(err);
assert.equal(ethConnector.web3.fromWei(_balance), 0);
cb();
@ -389,10 +389,10 @@ describe('MiniMeToken test', function(){
done();
});
});
it('Should move tokens in the child token from 2 to 3', function(done) {
it('Should move tokens in the cloned token from 2 to 3', function(done) {
async.series([
function(cb) {
miniMeTokenChild.transfer(ethConnector.accounts[2], ethConnector.web3.toWei(4), {
miniMeTokenCloned.transfer(ethConnector.accounts[2], ethConnector.web3.toWei(4), {
from: ethConnector.accounts[1],
gas: 200000},
function(err) {
@ -410,14 +410,14 @@ describe('MiniMeToken test', function(){
});
},
function(cb) {
miniMeTokenChild.balanceOf(ethConnector.accounts[1], function(err, _balance) {
miniMeTokenCloned.balanceOf(ethConnector.accounts[1], function(err, _balance) {
assert.ifError(err);
assert.equal(ethConnector.web3.fromWei(_balance), 2);
cb();
});
},
function(cb) {
miniMeTokenChild.balanceOf(ethConnector.accounts[2], function(err, _balance) {
miniMeTokenCloned.balanceOf(ethConnector.accounts[2], function(err, _balance) {
assert.ifError(err);
assert.equal(ethConnector.web3.fromWei(_balance), 5);
cb();
@ -438,49 +438,49 @@ describe('MiniMeToken test', function(){
});
},
function(cb) {
miniMeTokenChild.balanceOfAt(ethConnector.accounts[1], b[5], function(err, _balance) {
miniMeTokenCloned.balanceOfAt(ethConnector.accounts[1], b[5], function(err, _balance) {
assert.ifError(err);
assert.equal(ethConnector.web3.fromWei(_balance), 6);
cb();
});
},
function(cb) {
miniMeTokenChild.balanceOfAt(ethConnector.accounts[2], b[5], function(err, _balance) {
miniMeTokenCloned.balanceOfAt(ethConnector.accounts[2], b[5], function(err, _balance) {
assert.ifError(err);
assert.equal(ethConnector.web3.fromWei(_balance), 1);
cb();
});
},
function(cb) {
miniMeTokenChild.balanceOfAt(ethConnector.accounts[1], b[4], function(err, _balance) {
miniMeTokenCloned.balanceOfAt(ethConnector.accounts[1], b[4], function(err, _balance) {
assert.ifError(err);
assert.equal(ethConnector.web3.fromWei(_balance), 0);
cb();
});
},
function(cb) {
miniMeTokenChild.balanceOfAt(ethConnector.accounts[2], b[4], function(err, _balance) {
miniMeTokenCloned.balanceOfAt(ethConnector.accounts[2], b[4], function(err, _balance) {
assert.ifError(err);
assert.equal(ethConnector.web3.fromWei(_balance), 0);
cb();
});
},
function(cb) {
miniMeTokenChild.totalSupply(function(err, _totalSupply) {
miniMeTokenCloned.totalSupply(function(err, _totalSupply) {
assert.ifError(err);
assert.equal(ethConnector.web3.fromWei(_totalSupply), 7);
cb();
});
},
function(cb) {
miniMeTokenChild.totalSupplyAt(b[5], function(err, _totalSupply) {
miniMeTokenCloned.totalSupplyAt(b[5], function(err, _totalSupply) {
assert.ifError(err);
assert.equal(ethConnector.web3.fromWei(_totalSupply), 7);
cb();
});
},
function(cb) {
miniMeTokenChild.totalSupplyAt(b[4], function(err, _totalSupply) {
miniMeTokenCloned.totalSupplyAt(b[4], function(err, _totalSupply) {
assert.ifError(err);
assert.equal(ethConnector.web3.fromWei(_totalSupply), 0);
cb();