diff --git a/src/datatokens/Datatokens.ts b/src/datatokens/Datatokens.ts index d8d1201d..861dac66 100644 --- a/src/datatokens/Datatokens.ts +++ b/src/datatokens/Datatokens.ts @@ -1,5 +1,3 @@ -import Account from '../ocean/Account' - const defaultFactoryABI = require('@oceanprotocol/contracts/artifacts/development/Factory.json') const defaultDatatokensABI = require('@oceanprotocol/contracts/artifacts/development/DataTokenTemplate.json') @@ -35,13 +33,13 @@ export class DataTokens { /** * Create new datatoken * @param {String} metaDataStoreURI - * @param {Account} account + * @param {String} address * @return {Promise} datatoken address */ - public async create(metaDataStoreURI: string, account: Account): Promise { + public async create(metaDataStoreURI: string, address: string): Promise { // Create factory contract object const factory = new this.web3.eth.Contract(this.factoryABI, this.factoryAddress, { - from: account + from: address }) const estGas = await factory.methods .createToken(metaDataStoreURI) @@ -51,7 +49,7 @@ export class DataTokens { }) // Invoke createToken function of the contract const trxReceipt = await factory.methods.createToken(metaDataStoreURI).send({ - from: account, + from: address, gas: estGas + 1, gasPrice: '3000000000' }) @@ -69,129 +67,171 @@ export class DataTokens { * Approve * @param {String} dataTokenAddress * @param {String} toAddress - * @param {Number} amount - * @param {Account} account + * @param {Number} amount Number of datatokens, as number. Will be converted to wei + * @param {String} address * @return {Promise} transactionId */ public async approve( dataTokenAddress: string, spender: string, amount: number, - account: Account + address: string ): Promise { const datatoken = new this.web3.eth.Contract( this.datatokensABI, dataTokenAddress, - { from: account } + { from: address } ) - const trxReceipt = await datatoken.methods.approve(spender, amount).send() + const trxReceipt = await datatoken.methods + .approve(spender, this.web3.utils.toWei(String(amount))) + .send() return trxReceipt } /** * Mint * @param {String} dataTokenAddress - * @param {Account} account - * @param {Number} amount + * @param {String} address + * @param {Number} amount Number of datatokens, as number. Will be converted to wei * @param {String} toAddress - only if toAddress is different from the minter * @return {Promise} transactionId */ public async mint( dataTokenAddress: string, - account: Account, + address: string, amount: number, toAddress?: string ): Promise { - const address = toAddress || account + const destAddress = toAddress || address const datatoken = new this.web3.eth.Contract( this.datatokensABI, dataTokenAddress, - { from: account } + { from: address } ) const estGas = await datatoken.methods - .mint(address, amount) + .mint(destAddress, this.web3.utils.toWei(String(amount))) .estimateGas(function (err, estGas) { if (err) console.log('Datatokens: ' + err) return estGas }) - const trxReceipt = await datatoken.methods.mint(address, amount).send({ - from: account, - gas: estGas + 1, - gasPrice: '3000000000' - }) + const trxReceipt = await datatoken.methods + .mint(destAddress, this.web3.utils.toWei(String(amount))) + .send({ + from: address, + gas: estGas + 1, + gasPrice: '3000000000' + }) return trxReceipt } /** - * Transfer from Account to Address + * Transfer as number from address to toAddress * @param {String} dataTokenAddress * @param {String} toAddress - * @param {Number} amount - * @param {Account} account + * @param {Number} amount Number of datatokens, as number. Will be converted to wei + * @param {String} address * @return {Promise} transactionId */ public async transfer( dataTokenAddress: string, toAddress: string, amount: number, - account: Account + address: string + ): Promise { + return this.transferToken(dataTokenAddress, toAddress, amount, address) + } + + /** + * Transfer as number from address to toAddress + * @param {String} dataTokenAddress + * @param {String} toAddress + * @param {Number} amount Number of datatokens, as number. Will be converted to wei + * @param {String} address + * @return {Promise} transactionId + */ + public async transferToken( + dataTokenAddress: string, + toAddress: string, + amount: number, + address: string + ): Promise { + const weiAmount = this.web3.utils.toWei(String(amount)) + return this.transferWei(dataTokenAddress, toAddress, weiAmount, address) + } + + /** + * Transfer in wei from address to toAddress + * @param {String} dataTokenAddress + * @param {String} toAddress + * @param {Number} amount Number of datatokens, as number. Expressed as wei + * @param {String} address + * @return {Promise} transactionId + */ + public async transferWei( + dataTokenAddress: string, + toAddress: string, + amount: string, + address: string ): Promise { const datatoken = new this.web3.eth.Contract( this.datatokensABI, dataTokenAddress, - { from: account } + { from: address } ) - const trxReceipt = await datatoken.methods.transfer(toAddress, amount).send() + const trxReceipt = await datatoken.methods + .transfer(toAddress, String(amount)) + .send() return trxReceipt } /** - * Transfer from Address to Account (needs an Approve operation before) + * Transfer from fromAddress to address (needs an Approve operation before) * @param {String} dataTokenAddress * @param {String} fromAddress - * @param {Number} amount - * @param {Account} account + * @param {Number} amount Number of datatokens, as number. Will be converted to wei + * @param {String} address * @return {Promise} transactionId */ public async transferFrom( dataTokenAddress: string, fromAddress: string, amount: number, - account: string + address: string ): Promise { const datatoken = new this.web3.eth.Contract( this.datatokensABI, dataTokenAddress, - { from: account } + { from: address } ) const trxReceipt = await datatoken.methods - .transferFrom(fromAddress, account, amount) + .transferFrom(fromAddress, address, this.web3.utils.toWei(String(amount))) .send() return trxReceipt } /** - * Get Account Balance for datatoken + * Get Address Balance for datatoken * @param {String} dataTokenAddress - * @param {Account} account - * @return {Promise} balance + * @param {String} address + * @return {Promise} balance Number of datatokens, as number. Will be converted from wei */ - public async balance(dataTokenAddress: string, account: Account): Promise { + public async balance(dataTokenAddress: string, address: string): Promise { const datatoken = new this.web3.eth.Contract( this.datatokensABI, dataTokenAddress, - { from: account } + { from: address } ) - const trxReceipt = await datatoken.methods.balanceOf(account).call() - return trxReceipt + const balance = await datatoken.methods.balanceOf(address).call() + return this.web3.utils.fromWei(balance) } /** - * - * @param dataTokenAddress - * @param account + * Get Alloance + * @param {String } dataTokenAddress + * @param {String} owner + * @param {String} spender */ public async allowance( dataTokenAddress: string, @@ -204,19 +244,19 @@ export class DataTokens { { from: spender } ) const trxReceipt = await datatoken.methods.allowance(owner, spender).call() - return trxReceipt + return this.web3.utils.fromWei(trxReceipt) } /** Get Blob * @param {String} dataTokenAddress - * @param {Account} account + * @param {String} address * @return {Promise} string */ - public async getBlob(dataTokenAddress: string, account: Account): Promise { + public async getBlob(dataTokenAddress: string, address: string): Promise { const datatoken = new this.web3.eth.Contract( this.datatokensABI, dataTokenAddress, - { from: account.getId() } + { from: address } ) const trxReceipt = await datatoken.methods.blob().call() return trxReceipt @@ -224,14 +264,14 @@ export class DataTokens { /** Get Name * @param {String} dataTokenAddress - * @param {Account} account + * @param {String} address * @return {Promise} string */ - public async getName(dataTokenAddress: string, account: Account): Promise { + public async getName(dataTokenAddress: string, address: string): Promise { const datatoken = new this.web3.eth.Contract( this.datatokensABI, dataTokenAddress, - { from: account.getId() } + { from: address } ) const trxReceipt = await datatoken.methods.name().call() return trxReceipt @@ -239,14 +279,14 @@ export class DataTokens { /** Get Symbol * @param {String} dataTokenAddress - * @param {Account} account + * @param {String} address * @return {Promise} string */ - public async getSymbol(dataTokenAddress: string, account: Account): Promise { + public async getSymbol(dataTokenAddress: string, address: string): Promise { const datatoken = new this.web3.eth.Contract( this.datatokensABI, dataTokenAddress, - { from: account.getId() } + { from: address } ) const trxReceipt = await datatoken.methods.symbol().call() return trxReceipt @@ -254,16 +294,32 @@ export class DataTokens { /** Get Cap * @param {String} dataTokenAddress - * @param {Account} account + * @param {String} address * @return {Promise} string */ - public async getCap(dataTokenAddress: string, account: Account): Promise { + public async getCap(dataTokenAddress: string, address: string): Promise { const datatoken = new this.web3.eth.Contract( this.datatokensABI, dataTokenAddress, - { from: account.getId() } + { from: address } ) const trxReceipt = await datatoken.methods.cap().call() - return trxReceipt + return this.web3.utils.fromWei(trxReceipt) + } + + /** Convert from number to wei + * @param {Number} amount + * @return {Promise} string + */ + public toWei(amount) { + return this.web3.utils.toWei(String(amount)) + } + + /** Convert from wei to number + * @param {String} amount + * @return {Promise} string + */ + public fromWei(amount) { + return this.web3.utils.fromWei(amount) } } diff --git a/src/ddo/interfaces/MetadataMain.ts b/src/ddo/interfaces/MetadataMain.ts index c567dacc..6e420846 100644 --- a/src/ddo/interfaces/MetadataMain.ts +++ b/src/ddo/interfaces/MetadataMain.ts @@ -52,13 +52,6 @@ export interface MetadataMain { */ license: string - /** - * Price of the asset in vodka (attoOCEAN). It must be an integer encoded as a string. - * @type {string} - * @example "1000000000000000000" - */ - price: string - /** * Array of File objects including the encrypted file urls and some additional information. * @type {File[]} diff --git a/src/ddo/interfaces/Service.ts b/src/ddo/interfaces/Service.ts index 6e69c86b..a7ff2089 100644 --- a/src/ddo/interfaces/Service.ts +++ b/src/ddo/interfaces/Service.ts @@ -19,7 +19,7 @@ export interface ServiceAccessAttributes extends ServiceCommonAttributes { creator: string name: string datePublished: string - cost: number + cost: string timeout: number } } diff --git a/src/ocean/Assets.ts b/src/ocean/Assets.ts index daaa29fe..871a6084 100644 --- a/src/ocean/Assets.ts +++ b/src/ocean/Assets.ts @@ -73,7 +73,10 @@ export class Assets extends Instantiable { const metadataStoreURI = this.ocean.metadatastore.getURI() const jsonBlob = { t: 1, url: metadataStoreURI } const { datatokens } = this.ocean - dtAddress = await datatokens.create(JSON.stringify(jsonBlob), publisher) + dtAddress = await datatokens.create( + JSON.stringify(jsonBlob), + publisher.getId() + ) this.logger.log('DataToken creted') observer.next(CreateProgressStep.DataTokenCreated) } @@ -361,9 +364,17 @@ export class Assets extends Instantiable { return service } + /** + * Creates an access service + * @param {Account} creator + * @param {String} cost number of datatokens needed for this service, expressed in wei + * @param {String} datePublished + * @param {Number} timeout + * @return {Promise} service + */ public async createAccessServiceAttributes( creator: Account, - dtCost: number, + cost: string, datePublished: string, timeout: number = 0 ): Promise { @@ -375,7 +386,7 @@ export class Assets extends Instantiable { main: { creator: creator.getId(), datePublished, - cost: dtCost, + cost, timeout: timeout, name: 'dataAssetAccess' } diff --git a/src/ocean/Compute.ts b/src/ocean/Compute.ts index d3836477..3302321e 100644 --- a/src/ocean/Compute.ts +++ b/src/ocean/Compute.ts @@ -233,6 +233,16 @@ export class Compute extends Instantiable { } } + /** + * Creates a compute service + * @param {Account} consumerAccount + * @param {String} cost number of datatokens needed for this service, expressed in wei + * @param {String} datePublished + * @param {Object} providerAttributes + * @param {Object} computePrivacy + * @param {Number} timeout + * @return {Promise} service + */ public createComputeService( consumerAccount: Account, cost: string, diff --git a/test/integration/ComputeFlow.test.ts b/test/integration/ComputeFlow.test.ts index f48b5707..3b969055 100644 --- a/test/integration/ComputeFlow.test.ts +++ b/test/integration/ComputeFlow.test.ts @@ -114,7 +114,7 @@ describe('Marketplace flow', () => { }) it('Alice publishes dataset with a compute service that allows Raw Algo', async () => { - price = 2 // in datatoken + price = datatoken.toWei(2) // in datatoken cluster = ocean.compute.createClusterAttributes( 'Kubernetes', 'http://10.0.0.17/xxx' @@ -281,7 +281,7 @@ describe('Marketplace flow', () => { ) assert(order != null) const computeOrder = JSON.parse(order) - const tx = await datatoken.transfer( + const tx = await datatoken.transferWei( computeOrder['dataToken'], computeOrder['to'], computeOrder['numTokens'], @@ -349,7 +349,7 @@ describe('Marketplace flow', () => { bob.getId() ) const algoOrder = JSON.parse(orderalgo) - const algoTx = await datatoken.transfer( + const algoTx = await datatoken.transferWei( algoOrder['dataToken'], algoOrder['to'], algoOrder['numTokens'], @@ -364,7 +364,7 @@ describe('Marketplace flow', () => { ) assert(order != null) const computeOrder = JSON.parse(order) - const tx = await datatoken.transfer( + const tx = await datatoken.transferWei( computeOrder['dataToken'], computeOrder['to'], computeOrder['numTokens'], diff --git a/test/integration/Marketplaceflow.test.ts b/test/integration/Marketplaceflow.test.ts index 3ff1e2d6..db16ddc9 100644 --- a/test/integration/Marketplaceflow.test.ts +++ b/test/integration/Marketplaceflow.test.ts @@ -84,7 +84,7 @@ describe('Marketplace flow', () => { }) it('Alice publishes a dataset', async () => { - price = 10 // in datatoken + price = datatoken.toWei(10) // in datatoken const publishedDate = new Date(Date.now()).toISOString().split('.')[0] + 'Z' const timeout = 0 service1 = await ocean.assets.createAccessServiceAttributes( @@ -146,7 +146,7 @@ describe('Marketplace flow', () => { it('Marketplace posts asset for sale', async () => { accessService = await ocean.assets.getServiceByType(ddo.id, 'access') price = 20 - assert(accessService.attributes.main.cost * price === 200) + assert(accessService.attributes.main.cost * price === datatoken.toWei(200)) }) it('Bob gets datatokens', async () => { @@ -164,7 +164,7 @@ describe('Marketplace flow', () => { .order(ddo.id, accessService.type, bob.getId()) .then(async (res: string) => { res = JSON.parse(res) - return await datatoken.transfer( + return await datatoken.transferWei( res['dataToken'], res['to'], res['numTokens'],