-
Notifications
You must be signed in to change notification settings - Fork 10
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
Vilhelm Sjöberg
committed
Dec 11, 2020
1 parent
4720270
commit b399696
Showing
34 changed files
with
2,788 additions
and
414 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,5 @@ | ||
To run the tests: | ||
1. `npm install` to get Node.js dependencies | ||
2. `./start_conflux.sh` in a separate terminal, and start Ganache (for Ethereum tests) | ||
- Be sure to clone the `conflux-rust` repo, and within `start_conflux.sh`, set `conflux` to the location of your repo clone. | ||
3. `./run_unittests.sh` |
This file was deleted.
Oops, something went wrong.
This file was deleted.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file was deleted.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,45 @@ | ||
import { Chain } from './chain' | ||
import { printTest } from './utils' | ||
|
||
export async function runTest(chain: Chain) { | ||
await chain.deployContract('builtins') | ||
|
||
const _value = 5; | ||
|
||
let blockNumber = await chain.callMethod('f', [], {value: _value}) | ||
|
||
const [ | ||
_address, | ||
_origin, | ||
_caller, | ||
_callvalue, | ||
_coinbase, | ||
_timestamp, | ||
_number, | ||
_balance_this, | ||
_blockhash_prev | ||
] = await Promise.all([ | ||
chain.callMethod('get_address'), | ||
chain.callMethod('get_origin'), | ||
chain.callMethod('get_caller'), | ||
chain.callMethod('get_callvalue'), | ||
chain.callMethod('get_coinbase'), | ||
chain.callMethod('get_timestamp'), | ||
chain.callMethod('get_number'), | ||
chain.callMethod('get_balance_this'), | ||
chain.callMethod('get_blockhash_prev') | ||
]) | ||
|
||
printTest("address", _address == chain.getContractAddress()); | ||
printTest("origin", _origin == chain.getAccountAddress()); | ||
printTest("caller", _caller == chain.getAccountAddress()); | ||
printTest("callvalue", _callvalue == _value); | ||
printTest("timestamp", _timestamp == await chain.getBlockTimestamp(blockNumber)); | ||
printTest("number", _number == blockNumber); | ||
printTest("balance(this_address)", _balance_this == _value); | ||
printTest("blockhash(parent)", chain.hashToString(_blockhash_prev) | ||
== await chain.getBlockParentHash(blockNumber)); | ||
// the hash of the current block is not available, you just get 0x0 if you try, so we query the parent | ||
} | ||
|
||
export default { runTest } |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,17 @@ | ||
export interface Chain { | ||
deployContract(jsonFilename: string, constructorArgs?: any[]): void | ||
callMethod(func: string, args?: any[], options?: {}): any | ||
|
||
getContractAddress(): string | ||
getAccountAddress(): string | ||
getBlockTimestamp(blockNumber: number): Promise<number> | ||
getBlockParentHash(blockNumber: number): Promise<string> | ||
getEvents(): Promise<Event[]> | ||
|
||
hashToString(hash: any): string | ||
} | ||
|
||
export interface Event { | ||
signature: string | ||
args: {} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,11 @@ | ||
import sys | ||
import json | ||
|
||
s = sys.stdin.read() | ||
obj = json.loads(s) | ||
contracts = obj[list(obj)[0]] | ||
first_contract = contracts[list(contracts)[0]] | ||
first_contract['bytecode'] = '0x' + first_contract['bin'] | ||
del first_contract['bin'] | ||
first_contract['abi'] = json.loads(first_contract['abi']) | ||
print(json.dumps(first_contract)) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,121 @@ | ||
import { Conflux, Account } from 'js-conflux-sdk' | ||
import { Chain, Event } from './chain' | ||
import { getJsonFilename } from './utils' | ||
import _ from 'lodash' | ||
|
||
|
||
export class ConfluxChain implements Chain { | ||
private _conflux: Conflux | ||
private _contract | ||
private _genesisAccount: Account | ||
private _abi: any[] | ||
|
||
constructor(verbose=false) { | ||
let logger = this.getLogger(verbose) | ||
|
||
this._conflux = new Conflux({ | ||
url: 'http://localhost:12537', | ||
// defaultGasPrice: 1000, | ||
// defaultGas: 1000, | ||
// logger: this._logger, | ||
logger: logger, | ||
}) | ||
|
||
const genesisPrivateKey = | ||
'0xaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa' | ||
this._genesisAccount = this._conflux.wallet.addPrivateKey(genesisPrivateKey) | ||
} | ||
private getLogger(verbose: boolean): Logger { | ||
if (verbose) | ||
return console | ||
|
||
let logger: Logger = { | ||
info: function() {}, // Output nothing. | ||
error: function() {} | ||
} | ||
return logger | ||
} | ||
|
||
async deployContract(jsonFilename: string, constructorArgs=[]){ | ||
const {abi, bytecode} = require(getJsonFilename(jsonFilename)) | ||
this._contract = this._conflux.Contract({ abi, bytecode }) | ||
this._abi = abi | ||
|
||
const receipt = await this._contract | ||
.constructor(...constructorArgs) | ||
.sendTransaction({ from: this._genesisAccount }) | ||
.executed(); | ||
this._contract.address = receipt.contractCreated; | ||
} | ||
|
||
async callRead(func: string, args=[]){ | ||
return await this._contract[func](...args) | ||
} | ||
|
||
async callWrite(func: string, args=[], options={}) { | ||
// console.log("func: " + func) | ||
// console.log("args: " + args) | ||
// console.log("options: " + JSON.stringify(options)) | ||
let receipt = await this._contract[func](...args) | ||
.sendTransaction({ from: this._genesisAccount, ...options }) | ||
.executed(); | ||
return receipt.epochNumber | ||
} | ||
|
||
isRead(func: string): boolean { | ||
const f = this._abi.find(element => element.name == func) | ||
let readStates = [ "view", "pure" ] | ||
return readStates.includes(f.stateMutability) | ||
} | ||
|
||
async callMethod(func: string, args=[], options={}) { | ||
if (this.isRead(func)) { | ||
if (!_.isEmpty(options)) | ||
throw Error("Options specified but ignored.") | ||
return this.callRead(func, args) // returns the read value | ||
} else | ||
return this.callWrite(func, args, options) // returns the block number | ||
} | ||
|
||
// Getter functions | ||
getContractAddress(): string { | ||
return this._contract.address | ||
} | ||
getAccountAddress(): string { | ||
return this._genesisAccount.toString() | ||
} | ||
async getBlockTimestamp(blockNumber: number): Promise<number> { | ||
let receipt: any = await this._conflux.getBlockByEpochNumber(blockNumber) | ||
return receipt.timestamp | ||
} | ||
async getBlockParentHash(blockNumber: number): Promise<string> { | ||
let receipt: any = await this._conflux.getBlockByEpochNumber(blockNumber) | ||
return receipt.parentHash | ||
} | ||
|
||
hashToString(hash: any): string { | ||
return hash | ||
} | ||
|
||
async getEvents(): Promise<Event[]> { | ||
const logs = await this._conflux.getLogs({address: this._contract.address}) | ||
let decoded = logs.map(l => this._contract.abi.decodeLog(l)) | ||
return decoded.map(o => { | ||
if (!o) return o | ||
let substitutions = {type: "signature", object: "args"} | ||
for (const old_key in substitutions) { | ||
const new_key = substitutions[old_key] | ||
Object.defineProperty(o, new_key, | ||
Object.getOwnPropertyDescriptor(o, old_key)) | ||
delete o[old_key]; | ||
} | ||
return o | ||
} | ||
) | ||
} | ||
} | ||
|
||
interface Logger { | ||
info() | ||
error() | ||
} |
This file was deleted.
Oops, something went wrong.
This file was deleted.
Oops, something went wrong.
Oops, something went wrong.