Skip to content

Commit 4a79a97

Browse files
committed
Implemented buying artist tokens using profile funds
1 parent f467d79 commit 4a79a97

File tree

5 files changed

+68
-52
lines changed

5 files changed

+68
-52
lines changed

contracts/GSNProfile.sol

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,8 @@ contract GSNProfile is Initializable, GSNMultiOwnableRecipient {
3636
constructor(address _owner) public GSNMultiOwnableRecipient(_owner) {
3737
}
3838

39+
function() payable external {}
40+
3941
function addFile(bytes32 _cid, address _acl) public isOwner(_msgSender()) fileNotExists(_cid) {
4042
require(ACL(_acl).hasAdmin(address(this)));
4143

migrations/03_deploy_artist_token.js

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -13,10 +13,10 @@ const theta = 350000; // 35% in ppm
1313
const p0 = 1; // Price of internal token in external tokens.
1414
const initialRaise = 300; // Raise amount in external tokens.
1515
const friction = 20000; // 2% in ppm
16-
const gasPrice = 15000000000; // 15 gwei
16+
const gasPrice = 500000000000; // 500 gwei
1717
const hatchDurationSeconds = 3024000; // 5 weeks
18-
const hatchVestingDurationSeconds = 7890000; // 3 months
19-
const minExternalContribution = 100000;
18+
const hatchVestingDurationSeconds = 0; // 3 months
19+
const minExternalContribution = 10;
2020

2121
module.exports = function(deployer) {
2222
const fromAccount = process.env.ACCOUNT;

src/contracts/profile.js

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,8 @@ const {
1313

1414
const {
1515
buyArtistTokens,
16-
transfer: transferArtistToken
16+
transfer: transferArtistToken,
17+
getBalanceOf
1718
} = require('./artist_token');
1819

1920
const factoryScJSON = require('../../build/contracts/GSNProfileFactory.json');
@@ -208,7 +209,7 @@ module.exports.removeFile = (web3, { from, contractAddr, cid }) => {
208209
});
209210
};
210211

211-
module.exports.withdraw = (web3, {from, beneficiary, contractAddr, amountInPht}) => {
212+
const withdraw = module.exports.withdraw = (web3, {from, beneficiary, contractAddr, amountInPht}) => {
212213
Web3Wrapper.validator.validateAddress("from", from);
213214
Web3Wrapper.validator.validateAddress("beneficiary", beneficiary);
214215
Web3Wrapper.validator.validateAddress("contractAddr", contractAddr);
@@ -239,6 +240,7 @@ module.exports.withdrawArtistTokens = (web3, {from, beneficiary, contractAddr, a
239240

240241
module.exports.buyArtistTokens = async(web3, {from, contractAddr, artistTokenAddr, wphtAddr, amountInPht}) => {
241242
// Firstly we withdraw from profile contract enough PHT to buy artist token
243+
console.log(`Withdrawing ${amountInPht} from profile contract ${contractAddr}`);
242244
await withdraw(web3, {
243245
from,
244246
beneficiary: from,
@@ -247,16 +249,19 @@ module.exports.buyArtistTokens = async(web3, {from, contractAddr, artistTokenAdd
247249
});
248250

249251
// Then we proceed buying the tokens
250-
252+
console.log(`Buying ${amountInPht} of artist tokens`);
251253
const boughtAmountInBN = await buyArtistTokens(web3, {
252254
from,
253255
artistTokenAddr,
254256
wphtAddr,
255257
amountWeiBn: Web3Wrapper.utils.toBN(Web3Wrapper.utils.toWei(amountInPht))
256-
});
258+
}, true);
257259

258260
// At last we transfer tokens back to our profile contract
261+
console.log(`Transfer purchased artist tokens ${Web3Wrapper.utils.toPht(boughtAmountInBN)} back to profile contract ${contractAddr}`);
259262
await transferArtistToken(web3, {
263+
from,
264+
to: contractAddr,
260265
artistTokenAddr,
261266
amountInBn: boughtAmountInBN
262267
});

src/web3/addon/utils.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ const web3Utils = require('web3-utils');
99
const ethUtil = require('ethereumjs-util');
1010

1111
module.exports.toWei = (pht, unit = 'ether') => {
12-
return web3Utils.toWei(pht, unit)
12+
return web3Utils.toWei(`${pht}`, unit)
1313
};
1414

1515
module.exports.wei2pht = (n) => {

test/01_profile.js

Lines changed: 53 additions & 44 deletions
Original file line numberDiff line numberDiff line change
@@ -17,11 +17,12 @@ const ACL = artifacts.require("ACL");
1717

1818
const Web3 = require('../src/web3');
1919
const {
20-
buyArtistTokens
20+
buyArtistTokens,
2121
} = require('../src/contracts/profile');
2222

2323
const {
24-
getBalanceOf
24+
getBalanceOf,
25+
isArtistTokenHatched
2526
} = require('../src/contracts/artist_token');
2627

2728
contract('Profile', (accounts) => {
@@ -31,77 +32,85 @@ contract('Profile', (accounts) => {
3132
const ACCOUNT_DEFAULT_PASSWORD = 'test123';
3233
let profileInstance;
3334

35+
it('should deploy a multi ownable GSN Profile contract', async () => {
36+
const instanceProfile = await Profile.new(ROOT_ACCOUNT);
37+
38+
const isOwner = await instanceProfile.hasOwner(ROOT_ACCOUNT);
39+
assert.equal(isOwner, true, "message sender is correctly inserted as contract owner");
40+
});
41+
42+
it('should deploy a multi ownable GSN Profile contract, with recovery account', async () => {
43+
RECOVERY_ACCOUNT = await web3.eth.personal.newAccount(ACCOUNT_DEFAULT_PASSWORD);
44+
45+
const instanceProfile = await Profile.new(ROOT_ACCOUNT);
46+
await instanceProfile.addOwner(RECOVERY_ACCOUNT);
47+
48+
const isOwner = await instanceProfile.hasOwner(ROOT_ACCOUNT);
49+
assert.equal(isOwner, true, "message sender is correctly inserted as contract owner");
50+
51+
const isRecoveryAccountOwner = await instanceProfile.hasOwner(RECOVERY_ACCOUNT);
52+
assert.equal(isRecoveryAccountOwner, true, "recovery account is correctly inserted as contract owner");
53+
54+
profileInstance = instanceProfile;
55+
});
56+
57+
it('should deploy an ACL and add a file to the GSN Profile', async () => {
58+
const instanceAcl = await ACL.new(ROOT_ACCOUNT, false);
59+
const ipfsHashHex = web3.utils.asciiToHex('QmVkoUR7okDxVtoX');
60+
const ipfsHashBytes = web3.utils.hexToBytes(ipfsHashHex);
61+
62+
await instanceAcl.grantAdmin(profileInstance.address);
63+
await profileInstance.addFile(ipfsHashBytes, instanceAcl.address);
64+
65+
const hasFile = await profileInstance.hasFile(ipfsHashBytes);
66+
assert.equal(hasFile, true, "file was added correctly to profile");
67+
});
68+
3469
it('should buy artist tokens using profile contract funds', async () => {
3570
const amountInPht = 10;
36-
const txCost = 2;
37-
const artistTokenInstance = ArtistToken.deployed();
38-
const wphtInstance = WPHT.deployed();
71+
const txCost = 3;
72+
const artistTokenInstance = await ArtistToken.deployed();
73+
const wphtInstance = await WPHT.deployed();
74+
75+
assert.isTrue(await artistTokenInstance.isHatched());
76+
assert.isFalse(await artistTokenInstance.paused());
3977

4078
// Transfer little funds to recovery account to perform the claiming
4179
FAN_ACCOUNT = await web3.eth.personal.newAccount(ACCOUNT_DEFAULT_PASSWORD);
80+
await web3.eth.personal.unlockAccount(FAN_ACCOUNT, ACCOUNT_DEFAULT_PASSWORD, 1000);
81+
console.log(`Sending ${txCost} PHT to fan account`);
4282
await web3.eth.sendTransaction({
43-
from: FAN_ACCOUNT,
44-
to: profileInstance.address,
83+
from: ROOT_ACCOUNT,
84+
to: FAN_ACCOUNT,
4585
value: Web3.utils.toWei(`${txCost}`)
4686
});
4787

4888
// New fan profile contract
89+
console.log(`Deploying a new profile contract for the fan`);
4990
const fanProfileInstance = await Profile.new(FAN_ACCOUNT);
5091

5192
// Transfer funds to profile contract
93+
console.log(`Sending ${amountInPht} PHT to fan contract`);
5294
await web3.eth.sendTransaction({
5395
from: ROOT_ACCOUNT,
54-
to: profileInstance.address,
96+
to: fanProfileInstance.address,
5597
value: Web3.utils.toWei(`${amountInPht}`)
5698
});
5799

100+
console.log(`Buying ${amountInPht} artist tokens`);
58101
const bougthAmount = await buyArtistTokens(web3, {
102+
from: FAN_ACCOUNT,
59103
contractAddr: fanProfileInstance.address,
60104
artistTokenAddr: artistTokenInstance.address,
61105
wphtAddr: wphtInstance.address,
62-
from: RECOVERY_ACCOUNT,
63106
amountInPht
64107
});
65108

66109
const balanceOf = await getBalanceOf(web3, {
67110
artistTokenAddr: artistTokenInstance.address,
68-
accountAddr: profileInstance.address
111+
accountAddr: fanProfileInstance.address
69112
});
70113

71114
assert.equal(bougthAmount, balanceOf);
72115
});
73-
74-
// it('should deploy a multi ownable GSN Profile contract', async () => {
75-
// const instanceProfile = await Profile.new(ROOT_ACCOUNT);
76-
//
77-
// const isOwner = await instanceProfile.hasOwner(ROOT_ACCOUNT);
78-
// assert.equal(isOwner, true, "message sender is correctly inserted as contract owner");
79-
// });
80-
//
81-
// it('should deploy a multi ownable GSN Profile contract, with recovery account', async () => {
82-
// RECOVERY_ACCOUNT = await web3.eth.personal.newAccount(ACCOUNT_DEFAULT_PASSWORD);
83-
//
84-
// const instanceProfile = await Profile.new(ROOT_ACCOUNT);
85-
// await instanceProfile.addOwner(RECOVERY_ACCOUNT);
86-
//
87-
// const isOwner = await instanceProfile.hasOwner(ROOT_ACCOUNT);
88-
// assert.equal(isOwner, true, "message sender is correctly inserted as contract owner");
89-
//
90-
// const isRecoveryAccountOwner = await instanceProfile.hasOwner(RECOVERY_ACCOUNT);
91-
// assert.equal(isRecoveryAccountOwner, true, "recovery account is correctly inserted as contract owner");
92-
//
93-
// profileInstance = instanceProfile;
94-
// });
95-
//
96-
// it('should deploy an ACL and add a file to the GSN Profile', async () => {
97-
// const instanceAcl = await ACL.new(ROOT_ACCOUNT, false);
98-
// const ipfsHashHex = web3.utils.asciiToHex('QmVkoUR7okDxVtoX');
99-
// const ipfsHashBytes = web3.utils.hexToBytes(ipfsHashHex);
100-
//
101-
// await instanceAcl.grantAdmin(profileInstance.address);
102-
// await profileInstance.addFile(ipfsHashBytes, instanceAcl.address);
103-
//
104-
// const hasFile = await profileInstance.hasFile(ipfsHashBytes);
105-
// assert.equal(hasFile, true, "file was added correctly to profile");
106-
// });
107116
});

0 commit comments

Comments
 (0)