Merge pull request #39 from 0xProject/senderAccount
Make methods accept senderAccount
This commit is contained in:
commit
692a0fd965
23
src/0x.js.ts
23
src/0x.js.ts
@ -122,17 +122,11 @@ export class ZeroEx {
|
||||
this.token.invalidateContractInstances();
|
||||
}
|
||||
/**
|
||||
* Sets default account for sending transactions.
|
||||
* Get addresses via the supplied web3 instance available for sending transactions.
|
||||
*/
|
||||
public setTransactionSenderAccount(account: string): void {
|
||||
this.web3Wrapper.setDefaultAccount(account);
|
||||
}
|
||||
/**
|
||||
* Get the default account set for sending transactions.
|
||||
*/
|
||||
public async getTransactionSenderAccountIfExistsAsync(): Promise<string|undefined> {
|
||||
const senderAccountIfExists = await this.web3Wrapper.getSenderAddressIfExistsAsync();
|
||||
return senderAccountIfExists;
|
||||
public async getAvailableAddressesAsync(): Promise<string[]> {
|
||||
const availableAddresses = await this.web3Wrapper.getAvailableAddressesAsync();
|
||||
return availableAddresses;
|
||||
}
|
||||
/**
|
||||
* Computes the orderHash for a given order and returns it as a hex encoded string.
|
||||
@ -167,10 +161,9 @@ export class ZeroEx {
|
||||
* Signs an orderHash and returns it's elliptic curve signature
|
||||
* This method currently supports TestRPC, Geth and Parity above and below V1.6.6
|
||||
*/
|
||||
public async signOrderHashAsync(orderHashHex: string): Promise<ECSignature> {
|
||||
public async signOrderHashAsync(orderHashHex: string, signerAddress: string): Promise<ECSignature> {
|
||||
assert.isHexString('orderHashHex', orderHashHex);
|
||||
|
||||
const makerAddress = await this.web3Wrapper.getSenderAddressOrThrowAsync();
|
||||
await assert.isSenderAddressAsync('signerAddress', signerAddress, this.web3Wrapper);
|
||||
|
||||
let msgHashHex;
|
||||
const nodeVersion = await this.web3Wrapper.getNodeVersionAsync();
|
||||
@ -184,7 +177,7 @@ export class ZeroEx {
|
||||
msgHashHex = ethUtil.bufferToHex(msgHashBuff);
|
||||
}
|
||||
|
||||
const signature = await this.web3Wrapper.signTransactionAsync(makerAddress, msgHashHex);
|
||||
const signature = await this.web3Wrapper.signTransactionAsync(signerAddress, msgHashHex);
|
||||
|
||||
let signatureData;
|
||||
const [nodeVersionNumber] = findVersions(nodeVersion);
|
||||
@ -214,7 +207,7 @@ export class ZeroEx {
|
||||
r: ethUtil.bufferToHex(r),
|
||||
s: ethUtil.bufferToHex(s),
|
||||
};
|
||||
const isValidSignature = ZeroEx.isValidSignature(orderHashHex, ecSignature, makerAddress);
|
||||
const isValidSignature = ZeroEx.isValidSignature(orderHashHex, ecSignature, signerAddress);
|
||||
if (!isValidSignature) {
|
||||
throw new Error(ZeroExError.INVALID_SIGNATURE);
|
||||
}
|
||||
|
@ -57,7 +57,6 @@ export class ExchangeWrapper extends ContractWrapper {
|
||||
assert.doesConformToSchema('ecSignature', ecSignature, ecSignatureSchema);
|
||||
assert.isETHAddressHex('signerAddressHex', signerAddressHex);
|
||||
|
||||
const senderAddress = await this.web3Wrapper.getSenderAddressOrThrowAsync();
|
||||
const exchangeInstance = await this.getExchangeContractAsync();
|
||||
|
||||
const isValidSignature = await exchangeInstance.isValidSignature.call(
|
||||
@ -66,9 +65,6 @@ export class ExchangeWrapper extends ContractWrapper {
|
||||
ecSignature.v,
|
||||
ecSignature.r,
|
||||
ecSignature.s,
|
||||
{
|
||||
from: senderAddress,
|
||||
},
|
||||
);
|
||||
return isValidSignature;
|
||||
}
|
||||
@ -119,16 +115,16 @@ export class ExchangeWrapper extends ContractWrapper {
|
||||
* false forgoes this check and causes the smart contract to throw instead.
|
||||
*/
|
||||
public async fillOrderAsync(signedOrder: SignedOrder, fillTakerAmount: BigNumber.BigNumber,
|
||||
shouldCheckTransfer: boolean): Promise<void> {
|
||||
shouldCheckTransfer: boolean, takerAddress: string): Promise<void> {
|
||||
assert.doesConformToSchema('signedOrder',
|
||||
SchemaValidator.convertToJSONSchemaCompatibleObject(signedOrder as object),
|
||||
signedOrderSchema);
|
||||
assert.isBigNumber('fillTakerAmount', fillTakerAmount);
|
||||
assert.isBoolean('shouldCheckTransfer', shouldCheckTransfer);
|
||||
await assert.isSenderAddressAsync('takerAddress', takerAddress, this.web3Wrapper);
|
||||
|
||||
const senderAddress = await this.web3Wrapper.getSenderAddressOrThrowAsync();
|
||||
const exchangeInstance = await this.getExchangeContractAsync();
|
||||
await this.validateFillOrderAndThrowIfInvalidAsync(signedOrder, fillTakerAmount, senderAddress);
|
||||
await this.validateFillOrderAndThrowIfInvalidAsync(signedOrder, fillTakerAmount, takerAddress);
|
||||
|
||||
const orderAddresses: OrderAddresses = [
|
||||
signedOrder.maker,
|
||||
@ -154,7 +150,7 @@ export class ExchangeWrapper extends ContractWrapper {
|
||||
signedOrder.ecSignature.r,
|
||||
signedOrder.ecSignature.s,
|
||||
{
|
||||
from: senderAddress,
|
||||
from: takerAddress,
|
||||
},
|
||||
);
|
||||
const response: ContractResponse = await exchangeInstance.fill(
|
||||
@ -166,7 +162,7 @@ export class ExchangeWrapper extends ContractWrapper {
|
||||
signedOrder.ecSignature.r,
|
||||
signedOrder.ecSignature.s,
|
||||
{
|
||||
from: senderAddress,
|
||||
from: takerAddress,
|
||||
gas,
|
||||
},
|
||||
);
|
||||
@ -301,12 +297,10 @@ export class ExchangeWrapper extends ContractWrapper {
|
||||
private async isRoundingErrorAsync(takerTokenAmount: BigNumber.BigNumber,
|
||||
fillTakerAmount: BigNumber.BigNumber,
|
||||
makerTokenAmount: BigNumber.BigNumber): Promise<boolean> {
|
||||
await assert.isUserAddressAvailableAsync(this.web3Wrapper);
|
||||
const exchangeInstance = await this.getExchangeContractAsync();
|
||||
const senderAddress = await this.web3Wrapper.getSenderAddressOrThrowAsync();
|
||||
const isRoundingError = await exchangeInstance.isRoundingError.call(
|
||||
takerTokenAmount, fillTakerAmount, makerTokenAmount, {
|
||||
from: senderAddress,
|
||||
},
|
||||
takerTokenAmount, fillTakerAmount, makerTokenAmount,
|
||||
);
|
||||
return isRoundingError;
|
||||
}
|
||||
|
@ -25,6 +25,7 @@ export class TokenWrapper extends ContractWrapper {
|
||||
public async getBalanceAsync(tokenAddress: string, ownerAddress: string): Promise<BigNumber.BigNumber> {
|
||||
assert.isETHAddressHex('ownerAddress', ownerAddress);
|
||||
assert.isETHAddressHex('tokenAddress', tokenAddress);
|
||||
await assert.isUserAddressAvailableAsync(this.web3Wrapper);
|
||||
|
||||
const tokenContract = await this.getTokenContractAsync(tokenAddress);
|
||||
let balance = await tokenContract.balanceOf.call(ownerAddress);
|
||||
@ -38,7 +39,7 @@ export class TokenWrapper extends ContractWrapper {
|
||||
*/
|
||||
public async setAllowanceAsync(tokenAddress: string, ownerAddress: string, spenderAddress: string,
|
||||
amountInBaseUnits: BigNumber.BigNumber): Promise<void> {
|
||||
assert.isETHAddressHex('ownerAddress', ownerAddress);
|
||||
await assert.isSenderAddressAsync('ownerAddress', ownerAddress, this.web3Wrapper);
|
||||
assert.isETHAddressHex('spenderAddress', spenderAddress);
|
||||
assert.isETHAddressHex('tokenAddress', tokenAddress);
|
||||
assert.isBigNumber('amountInBaseUnits', amountInBaseUnits);
|
||||
@ -60,6 +61,7 @@ export class TokenWrapper extends ContractWrapper {
|
||||
public async getAllowanceAsync(tokenAddress: string, ownerAddress: string, spenderAddress: string) {
|
||||
assert.isETHAddressHex('ownerAddress', ownerAddress);
|
||||
assert.isETHAddressHex('tokenAddress', tokenAddress);
|
||||
await assert.isUserAddressAvailableAsync(this.web3Wrapper);
|
||||
|
||||
const tokenContract = await this.getTokenContractAsync(tokenAddress);
|
||||
let allowanceInBaseUnits = await tokenContract.allowance.call(ownerAddress, spenderAddress);
|
||||
@ -97,7 +99,7 @@ export class TokenWrapper extends ContractWrapper {
|
||||
public async transferAsync(tokenAddress: string, fromAddress: string, toAddress: string,
|
||||
amountInBaseUnits: BigNumber.BigNumber): Promise<void> {
|
||||
assert.isETHAddressHex('tokenAddress', tokenAddress);
|
||||
assert.isETHAddressHex('fromAddress', fromAddress);
|
||||
await assert.isSenderAddressAsync('fromAddress', fromAddress, this.web3Wrapper);
|
||||
assert.isETHAddressHex('toAddress', toAddress);
|
||||
assert.isBigNumber('amountInBaseUnits', amountInBaseUnits);
|
||||
|
||||
@ -123,9 +125,8 @@ export class TokenWrapper extends ContractWrapper {
|
||||
assert.isETHAddressHex('tokenAddress', tokenAddress);
|
||||
assert.isETHAddressHex('fromAddress', fromAddress);
|
||||
assert.isETHAddressHex('toAddress', toAddress);
|
||||
assert.isETHAddressHex('senderAddress', senderAddress);
|
||||
await assert.isSenderAddressAsync('senderAddress', senderAddress, this.web3Wrapper);
|
||||
assert.isBigNumber('amountInBaseUnits', amountInBaseUnits);
|
||||
await assert.isSenderAddressAvailableAsync(this.web3Wrapper, senderAddress);
|
||||
|
||||
const tokenContract = await this.getTokenContractAsync(tokenAddress);
|
||||
|
||||
|
@ -47,7 +47,7 @@ export type CreateContractEvent = (indexFilterValues: IndexFilterValues,
|
||||
export interface ExchangeContract {
|
||||
isValidSignature: {
|
||||
call: (signerAddressHex: string, dataHex: string, v: number, r: string, s: string,
|
||||
txOpts: TxOpts) => Promise<boolean>;
|
||||
txOpts?: TxOpts) => Promise<boolean>;
|
||||
};
|
||||
LogFill: CreateContractEvent;
|
||||
LogCancel: CreateContractEvent;
|
||||
@ -60,7 +60,7 @@ export interface ExchangeContract {
|
||||
};
|
||||
isRoundingError: {
|
||||
call: (takerTokenAmount: BigNumber.BigNumber, fillTakerAmount: BigNumber.BigNumber,
|
||||
makerTokenAmount: BigNumber.BigNumber, txOpts: TxOpts) => Promise<boolean>;
|
||||
makerTokenAmount: BigNumber.BigNumber, txOpts?: TxOpts) => Promise<boolean>;
|
||||
};
|
||||
fill: {
|
||||
(orderAddresses: OrderAddresses, orderValues: OrderValues, fillAmount: BigNumber.BigNumber,
|
||||
|
@ -26,10 +26,20 @@ export const assert = {
|
||||
const web3 = new Web3();
|
||||
this.assert(web3.isAddress(value), this.typeAssertionMessage(variableName, 'ETHAddressHex', value));
|
||||
},
|
||||
async isSenderAddressAvailableAsync(web3Wrapper: Web3Wrapper, senderAddress: string) {
|
||||
const isSenderAddressAvailable = await web3Wrapper.isSenderAddressAvailableAsync(senderAddress);
|
||||
assert.assert(isSenderAddressAvailable, 'Specified senderAddress isn\'t available through the \
|
||||
supplied web3 instance');
|
||||
async isSenderAddressAsync(variableName: string, senderAddressHex: string,
|
||||
web3Wrapper: Web3Wrapper): Promise<void> {
|
||||
assert.isETHAddressHex(variableName, senderAddressHex);
|
||||
await assert.isSenderAddressAvailableAsync(web3Wrapper, variableName, senderAddressHex);
|
||||
},
|
||||
async isSenderAddressAvailableAsync(web3Wrapper: Web3Wrapper, variableName: string,
|
||||
senderAddressHex: string): Promise<void> {
|
||||
const isSenderAddressAvailable = await web3Wrapper.isSenderAddressAvailableAsync(senderAddressHex);
|
||||
assert.assert(isSenderAddressAvailable, `Specified ${variableName} ${senderAddressHex} isn't available \
|
||||
through the supplied web3 instance`);
|
||||
},
|
||||
async isUserAddressAvailableAsync(web3Wrapper: Web3Wrapper): Promise<void> {
|
||||
const availableAddresses = await web3Wrapper.getAvailableAddressesAsync();
|
||||
this.assert(!_.isEmpty(availableAddresses), 'No addresses were available on the provided web3 instance');
|
||||
},
|
||||
isNumber(variableName: string, value: number): void {
|
||||
this.assert(_.isFinite(value), this.typeAssertionMessage(variableName, 'number', value));
|
||||
|
@ -17,26 +17,8 @@ export class Web3Wrapper {
|
||||
public isAddress(address: string): boolean {
|
||||
return this.web3.isAddress(address);
|
||||
}
|
||||
public getDefaultAccount(): string {
|
||||
return this.web3.eth.defaultAccount;
|
||||
}
|
||||
public setDefaultAccount(address: string): void {
|
||||
this.web3.eth.defaultAccount = address;
|
||||
}
|
||||
public async getSenderAddressOrThrowAsync(): Promise<string> {
|
||||
const senderAddressIfExists = await this.getSenderAddressIfExistsAsync();
|
||||
assert.assert(!_.isUndefined(senderAddressIfExists), ZeroExError.USER_HAS_NO_ASSOCIATED_ADDRESSES);
|
||||
return senderAddressIfExists as string;
|
||||
}
|
||||
public async getFirstAddressIfExistsAsync(): Promise<string|undefined> {
|
||||
const addresses = await this.getAvailableSenderAddressesAsync();
|
||||
if (_.isEmpty(addresses)) {
|
||||
return undefined;
|
||||
}
|
||||
return addresses[0];
|
||||
}
|
||||
public async isSenderAddressAvailableAsync(senderAddress: string): Promise<boolean> {
|
||||
const addresses = await this.getAvailableSenderAddressesAsync();
|
||||
const addresses = await this.getAvailableAddressesAsync();
|
||||
return _.includes(addresses, senderAddress);
|
||||
}
|
||||
public async getNodeVersionAsync(): Promise<string> {
|
||||
@ -73,15 +55,7 @@ export class Web3Wrapper {
|
||||
const {timestamp} = await promisify(this.web3.eth.getBlock)(blockHash);
|
||||
return timestamp;
|
||||
}
|
||||
public async getSenderAddressIfExistsAsync(): Promise<string|undefined> {
|
||||
const defaultAccount = this.web3.eth.defaultAccount;
|
||||
if (!_.isUndefined(defaultAccount)) {
|
||||
return defaultAccount;
|
||||
}
|
||||
const firstAccount = await this.getFirstAddressIfExistsAsync();
|
||||
return firstAccount;
|
||||
}
|
||||
private async getAvailableSenderAddressesAsync(): Promise<string[]> {
|
||||
public async getAvailableAddressesAsync(): Promise<string[]> {
|
||||
const addresses: string[] = await promisify(this.web3.eth.getAccounts)();
|
||||
return addresses;
|
||||
}
|
||||
|
@ -188,6 +188,13 @@ describe('ZeroEx library', () => {
|
||||
});
|
||||
describe('#signOrderHashAsync', () => {
|
||||
let stubs: Sinon.SinonStub[] = [];
|
||||
let makerAddress: string;
|
||||
const web3 = web3Factory.create();
|
||||
const zeroEx = new ZeroEx(web3);
|
||||
before(async () => {
|
||||
const availableAddreses = await zeroEx.getAvailableAddressesAsync();
|
||||
makerAddress = availableAddreses[0];
|
||||
});
|
||||
afterEach(() => {
|
||||
// clean up any stubs after the test has completed
|
||||
_.each(stubs, s => s.restore());
|
||||
@ -200,10 +207,7 @@ describe('ZeroEx library', () => {
|
||||
r: '0x61a3ed31b43c8780e905a260a35faefcc527be7516aa11c0256729b5b351bc33',
|
||||
s: '0x40349190569279751135161d22529dc25add4f6069af05be04cacbda2ace2254',
|
||||
};
|
||||
|
||||
const web3 = web3Factory.create();
|
||||
const zeroEx = new ZeroEx(web3);
|
||||
const ecSignature = await zeroEx.signOrderHashAsync(orderHash);
|
||||
const ecSignature = await zeroEx.signOrderHashAsync(orderHash, makerAddress);
|
||||
expect(ecSignature).to.deep.equal(expectedECSignature);
|
||||
});
|
||||
it ('should return the correct ECSignature on Parity > V1.6.6', async () => {
|
||||
@ -216,9 +220,6 @@ describe('ZeroEx library', () => {
|
||||
r: '0x22109d11d79cb8bf96ed88625e1cd9558800c4073332a9a02857499883ee5ce3',
|
||||
s: '0x050aa3cc1f2c435e67e114cdce54b9527b4f50548342401bc5d2b77adbdacb02',
|
||||
};
|
||||
|
||||
const web3 = web3Factory.create();
|
||||
const zeroEx = new ZeroEx(web3);
|
||||
stubs = [
|
||||
Sinon.stub((zeroEx as any).web3Wrapper, 'getNodeVersionAsync')
|
||||
.returns(Promise.resolve(newParityNodeVersion)),
|
||||
@ -227,7 +228,7 @@ describe('ZeroEx library', () => {
|
||||
Sinon.stub(ZeroEx, 'isValidSignature').returns(true),
|
||||
];
|
||||
|
||||
const ecSignature = await zeroEx.signOrderHashAsync(orderHash);
|
||||
const ecSignature = await zeroEx.signOrderHashAsync(orderHash, makerAddress);
|
||||
expect(ecSignature).to.deep.equal(expectedECSignature);
|
||||
});
|
||||
it ('should return the correct ECSignature on Parity < V1.6.6', async () => {
|
||||
@ -240,9 +241,6 @@ describe('ZeroEx library', () => {
|
||||
r: '0xc80bedc6756722672753413efdd749b5adbd4fd552595f59c13427407ee9aee0',
|
||||
s: '0x2dea66f25a608bbae457e020fb6decb763deb8b7192abab624997242da248960',
|
||||
};
|
||||
|
||||
const web3 = web3Factory.create();
|
||||
const zeroEx = new ZeroEx(web3);
|
||||
stubs = [
|
||||
Sinon.stub((zeroEx as any).web3Wrapper, 'getNodeVersionAsync')
|
||||
.returns(Promise.resolve(newParityNodeVersion)),
|
||||
@ -251,7 +249,7 @@ describe('ZeroEx library', () => {
|
||||
Sinon.stub(ZeroEx, 'isValidSignature').returns(true),
|
||||
];
|
||||
|
||||
const ecSignature = await zeroEx.signOrderHashAsync(orderHash);
|
||||
const ecSignature = await zeroEx.signOrderHashAsync(orderHash, makerAddress);
|
||||
expect(ecSignature).to.deep.equal(expectedECSignature);
|
||||
});
|
||||
});
|
||||
|
33
test/assert_test.ts
Normal file
33
test/assert_test.ts
Normal file
@ -0,0 +1,33 @@
|
||||
import * as chai from 'chai';
|
||||
import 'mocha';
|
||||
import {ZeroEx} from '../src/0x.js';
|
||||
import {assert} from '../src/utils/assert';
|
||||
import {web3Factory} from './utils/web3_factory';
|
||||
|
||||
const expect = chai.expect;
|
||||
|
||||
describe('Assertion library', () => {
|
||||
const web3 = web3Factory.create();
|
||||
const zeroEx = new ZeroEx(web3);
|
||||
describe('#isSenderAddressHexAsync', () => {
|
||||
it('throws when address is invalid', async () => {
|
||||
const address = '0xdeadbeef';
|
||||
const varName = 'address';
|
||||
return expect(assert.isSenderAddressAsync(varName, address, (zeroEx as any).web3Wrapper))
|
||||
.to.be.rejectedWith(`Expected ${varName} to be of type ETHAddressHex, encountered: ${address}`);
|
||||
});
|
||||
it('throws when address is unavailable', async () => {
|
||||
const validUnrelatedAddress = '0x8b0292b11a196601eddce54b665cafeca0347d42';
|
||||
const varName = 'address';
|
||||
return expect(assert.isSenderAddressAsync(varName, validUnrelatedAddress, (zeroEx as any).web3Wrapper))
|
||||
.to.be.rejectedWith(`Specified ${varName} ${validUnrelatedAddress} \
|
||||
isn't available through the supplied web3 instance`);
|
||||
});
|
||||
it('doesn\'t throw if address is available', async () => {
|
||||
const availableAddress = (await zeroEx.getAvailableAddressesAsync())[0];
|
||||
const varName = 'address';
|
||||
return expect(assert.isSenderAddressAsync(varName, availableAddress, (zeroEx as any).web3Wrapper))
|
||||
.to.become(undefined);
|
||||
});
|
||||
});
|
||||
});
|
@ -136,9 +136,6 @@ describe('ExchangeWrapper', () => {
|
||||
makerTokenAddress = makerToken.address;
|
||||
takerTokenAddress = takerToken.address;
|
||||
});
|
||||
afterEach('reset default account', () => {
|
||||
zeroEx.setTransactionSenderAccount(userAddresses[0]);
|
||||
});
|
||||
describe('failed fills', () => {
|
||||
it('should throw when the fill amount is zero', async () => {
|
||||
const fillableAmount = new BigNumber(5);
|
||||
@ -146,9 +143,8 @@ describe('ExchangeWrapper', () => {
|
||||
makerTokenAddress, takerTokenAddress, makerAddress, takerAddress, fillableAmount,
|
||||
);
|
||||
const zeroFillAmount = new BigNumber(0);
|
||||
zeroEx.setTransactionSenderAccount(takerAddress);
|
||||
return expect(zeroEx.exchange.fillOrderAsync(
|
||||
signedOrder, zeroFillAmount, shouldCheckTransfer,
|
||||
signedOrder, zeroFillAmount, shouldCheckTransfer, takerAddress,
|
||||
)).to.be.rejectedWith(ExchangeContractErrs.ORDER_REMAINING_FILL_AMOUNT_ZERO);
|
||||
});
|
||||
it('should throw when sender is not a taker', async () => {
|
||||
@ -157,7 +153,7 @@ describe('ExchangeWrapper', () => {
|
||||
makerTokenAddress, takerTokenAddress, makerAddress, takerAddress, fillableAmount,
|
||||
);
|
||||
return expect(zeroEx.exchange.fillOrderAsync(
|
||||
signedOrder, fillTakerAmount, shouldCheckTransfer,
|
||||
signedOrder, fillTakerAmount, shouldCheckTransfer, takerAddress,
|
||||
)).to.be.rejectedWith(ExchangeContractErrs.TRANSACTION_SENDER_IS_NOT_FILL_ORDER_TAKER);
|
||||
});
|
||||
it('should throw when order is expired', async () => {
|
||||
@ -166,9 +162,8 @@ describe('ExchangeWrapper', () => {
|
||||
const signedOrder = await fillScenarios.createFillableSignedOrderAsync(
|
||||
makerTokenAddress, takerTokenAddress, makerAddress, takerAddress, fillableAmount, expirationInPast,
|
||||
);
|
||||
zeroEx.setTransactionSenderAccount(takerAddress);
|
||||
return expect(zeroEx.exchange.fillOrderAsync(
|
||||
signedOrder, fillTakerAmount, shouldCheckTransfer,
|
||||
signedOrder, fillTakerAmount, shouldCheckTransfer, takerAddress,
|
||||
)).to.be.rejectedWith(ExchangeContractErrs.ORDER_FILL_EXPIRED);
|
||||
});
|
||||
describe('should throw when not enough balance or allowance to fulfill the order', () => {
|
||||
@ -185,36 +180,32 @@ describe('ExchangeWrapper', () => {
|
||||
await zeroEx.token.transferAsync(
|
||||
takerTokenAddress, takerAddress, coinbase, balanceToSubtractFromMaker,
|
||||
);
|
||||
zeroEx.setTransactionSenderAccount(takerAddress);
|
||||
return expect(zeroEx.exchange.fillOrderAsync(
|
||||
signedOrder, fillTakerAmount, shouldCheckTransfer,
|
||||
signedOrder, fillTakerAmount, shouldCheckTransfer, takerAddress,
|
||||
)).to.be.rejectedWith(ExchangeContractErrs.INSUFFICIENT_TAKER_BALANCE);
|
||||
});
|
||||
it('should throw when taker allowance is less than fill amount', async () => {
|
||||
const newAllowanceWhichIsLessThanFillAmount = fillTakerAmount.minus(lackingAllowance);
|
||||
await zeroEx.token.setProxyAllowanceAsync(takerTokenAddress, takerAddress,
|
||||
newAllowanceWhichIsLessThanFillAmount);
|
||||
zeroEx.setTransactionSenderAccount(takerAddress);
|
||||
return expect(zeroEx.exchange.fillOrderAsync(
|
||||
signedOrder, fillTakerAmount, shouldCheckTransfer,
|
||||
signedOrder, fillTakerAmount, shouldCheckTransfer, takerAddress,
|
||||
)).to.be.rejectedWith(ExchangeContractErrs.INSUFFICIENT_TAKER_ALLOWANCE);
|
||||
});
|
||||
it('should throw when maker balance is less than maker fill amount', async () => {
|
||||
await zeroEx.token.transferAsync(
|
||||
makerTokenAddress, makerAddress, coinbase, balanceToSubtractFromMaker,
|
||||
);
|
||||
zeroEx.setTransactionSenderAccount(takerAddress);
|
||||
return expect(zeroEx.exchange.fillOrderAsync(
|
||||
signedOrder, fillTakerAmount, shouldCheckTransfer,
|
||||
signedOrder, fillTakerAmount, shouldCheckTransfer, takerAddress,
|
||||
)).to.be.rejectedWith(ExchangeContractErrs.INSUFFICIENT_MAKER_BALANCE);
|
||||
});
|
||||
it('should throw when maker allowance is less than maker fill amount', async () => {
|
||||
const newAllowanceWhichIsLessThanFillAmount = fillTakerAmount.minus(lackingAllowance);
|
||||
await zeroEx.token.setProxyAllowanceAsync(makerTokenAddress, makerAddress,
|
||||
newAllowanceWhichIsLessThanFillAmount);
|
||||
zeroEx.setTransactionSenderAccount(takerAddress);
|
||||
return expect(zeroEx.exchange.fillOrderAsync(
|
||||
signedOrder, fillTakerAmount, shouldCheckTransfer,
|
||||
signedOrder, fillTakerAmount, shouldCheckTransfer, takerAddress,
|
||||
)).to.be.rejectedWith(ExchangeContractErrs.INSUFFICIENT_MAKER_ALLOWANCE);
|
||||
});
|
||||
});
|
||||
@ -226,9 +217,8 @@ describe('ExchangeWrapper', () => {
|
||||
makerAmount, takerAmount,
|
||||
);
|
||||
const fillTakerAmountThatCausesRoundingError = new BigNumber(3);
|
||||
zeroEx.setTransactionSenderAccount(takerAddress);
|
||||
return expect(zeroEx.exchange.fillOrderAsync(
|
||||
signedOrder, fillTakerAmountThatCausesRoundingError, shouldCheckTransfer,
|
||||
signedOrder, fillTakerAmountThatCausesRoundingError, shouldCheckTransfer, takerAddress,
|
||||
)).to.be.rejectedWith(ExchangeContractErrs.ORDER_FILL_ROUNDING_ERROR);
|
||||
});
|
||||
describe('should throw when not enough balance or allowance to pay fees', () => {
|
||||
@ -241,7 +231,6 @@ describe('ExchangeWrapper', () => {
|
||||
makerTokenAddress, takerTokenAddress, makerFee, takerFee,
|
||||
makerAddress, takerAddress, fillableAmount, feeRecipient,
|
||||
);
|
||||
zeroEx.setTransactionSenderAccount(takerAddress);
|
||||
});
|
||||
it('should throw when maker doesn\'t have enough balance to pay fees', async () => {
|
||||
const balanceToSubtractFromMaker = new BigNumber(1);
|
||||
@ -249,7 +238,7 @@ describe('ExchangeWrapper', () => {
|
||||
zrxTokenAddress, makerAddress, coinbase, balanceToSubtractFromMaker,
|
||||
);
|
||||
return expect(zeroEx.exchange.fillOrderAsync(
|
||||
signedOrder, fillTakerAmount, shouldCheckTransfer,
|
||||
signedOrder, fillTakerAmount, shouldCheckTransfer, takerAddress,
|
||||
)).to.be.rejectedWith(ExchangeContractErrs.INSUFFICIENT_MAKER_FEE_BALANCE);
|
||||
});
|
||||
it('should throw when maker doesn\'t have enough allowance to pay fees', async () => {
|
||||
@ -257,7 +246,7 @@ describe('ExchangeWrapper', () => {
|
||||
await zeroEx.token.setProxyAllowanceAsync(zrxTokenAddress, makerAddress,
|
||||
newAllowanceWhichIsLessThanFees);
|
||||
return expect(zeroEx.exchange.fillOrderAsync(
|
||||
signedOrder, fillTakerAmount, shouldCheckTransfer,
|
||||
signedOrder, fillTakerAmount, shouldCheckTransfer, takerAddress,
|
||||
)).to.be.rejectedWith(ExchangeContractErrs.INSUFFICIENT_MAKER_FEE_ALLOWANCE);
|
||||
});
|
||||
it('should throw when taker doesn\'t have enough balance to pay fees', async () => {
|
||||
@ -266,7 +255,7 @@ describe('ExchangeWrapper', () => {
|
||||
zrxTokenAddress, takerAddress, coinbase, balanceToSubtractFromTaker,
|
||||
);
|
||||
return expect(zeroEx.exchange.fillOrderAsync(
|
||||
signedOrder, fillTakerAmount, shouldCheckTransfer,
|
||||
signedOrder, fillTakerAmount, shouldCheckTransfer, takerAddress,
|
||||
)).to.be.rejectedWith(ExchangeContractErrs.INSUFFICIENT_TAKER_FEE_BALANCE);
|
||||
});
|
||||
it('should throw when taker doesn\'t have enough allowance to pay fees', async () => {
|
||||
@ -274,7 +263,7 @@ describe('ExchangeWrapper', () => {
|
||||
await zeroEx.token.setProxyAllowanceAsync(zrxTokenAddress, takerAddress,
|
||||
newAllowanceWhichIsLessThanFees);
|
||||
return expect(zeroEx.exchange.fillOrderAsync(
|
||||
signedOrder, fillTakerAmount, shouldCheckTransfer,
|
||||
signedOrder, fillTakerAmount, shouldCheckTransfer, takerAddress,
|
||||
)).to.be.rejectedWith(ExchangeContractErrs.INSUFFICIENT_TAKER_FEE_ALLOWANCE);
|
||||
});
|
||||
});
|
||||
@ -293,8 +282,7 @@ describe('ExchangeWrapper', () => {
|
||||
.to.be.bignumber.equal(0);
|
||||
expect(await zeroEx.token.getBalanceAsync(takerTokenAddress, takerAddress))
|
||||
.to.be.bignumber.equal(fillableAmount);
|
||||
zeroEx.setTransactionSenderAccount(takerAddress);
|
||||
await zeroEx.exchange.fillOrderAsync(signedOrder, fillTakerAmount, shouldCheckTransfer);
|
||||
await zeroEx.exchange.fillOrderAsync(signedOrder, fillTakerAmount, shouldCheckTransfer, takerAddress);
|
||||
expect(await zeroEx.token.getBalanceAsync(makerTokenAddress, makerAddress))
|
||||
.to.be.bignumber.equal(fillableAmount.minus(fillTakerAmount));
|
||||
expect(await zeroEx.token.getBalanceAsync(takerTokenAddress, makerAddress))
|
||||
@ -310,8 +298,7 @@ describe('ExchangeWrapper', () => {
|
||||
makerTokenAddress, takerTokenAddress, makerAddress, takerAddress, fillableAmount,
|
||||
);
|
||||
const partialFillAmount = new BigNumber(3);
|
||||
zeroEx.setTransactionSenderAccount(takerAddress);
|
||||
await zeroEx.exchange.fillOrderAsync(signedOrder, partialFillAmount, shouldCheckTransfer);
|
||||
await zeroEx.exchange.fillOrderAsync(signedOrder, partialFillAmount, shouldCheckTransfer, takerAddress);
|
||||
expect(await zeroEx.token.getBalanceAsync(makerTokenAddress, makerAddress))
|
||||
.to.be.bignumber.equal(fillableAmount.minus(partialFillAmount));
|
||||
expect(await zeroEx.token.getBalanceAsync(takerTokenAddress, makerAddress))
|
||||
@ -329,8 +316,7 @@ describe('ExchangeWrapper', () => {
|
||||
makerTokenAddress, takerTokenAddress, makerFee, takerFee,
|
||||
makerAddress, takerAddress, fillableAmount, feeRecipient,
|
||||
);
|
||||
zeroEx.setTransactionSenderAccount(takerAddress);
|
||||
await zeroEx.exchange.fillOrderAsync(signedOrder, fillTakerAmount, shouldCheckTransfer);
|
||||
await zeroEx.exchange.fillOrderAsync(signedOrder, fillTakerAmount, shouldCheckTransfer, takerAddress);
|
||||
expect(await zeroEx.token.getBalanceAsync(zrxTokenAddress, feeRecipient))
|
||||
.to.be.bignumber.equal(makerFee.plus(takerFee));
|
||||
});
|
||||
@ -445,8 +431,9 @@ describe('ExchangeWrapper', () => {
|
||||
done();
|
||||
});
|
||||
const fillTakerAmountInBaseUnits = new BigNumber(1);
|
||||
zeroEx.setTransactionSenderAccount(takerAddress);
|
||||
await zeroEx.exchange.fillOrderAsync(signedOrder, fillTakerAmountInBaseUnits, shouldCheckTransfer);
|
||||
await zeroEx.exchange.fillOrderAsync(
|
||||
signedOrder, fillTakerAmountInBaseUnits, shouldCheckTransfer, takerAddress,
|
||||
);
|
||||
})();
|
||||
});
|
||||
it('Outstanding subscriptions are cancelled when zeroEx.setProviderAsync called', (done: DoneCallback) => {
|
||||
@ -471,8 +458,9 @@ describe('ExchangeWrapper', () => {
|
||||
});
|
||||
|
||||
const fillTakerAmountInBaseUnits = new BigNumber(1);
|
||||
zeroEx.setTransactionSenderAccount(takerAddress);
|
||||
await zeroEx.exchange.fillOrderAsync(signedOrder, fillTakerAmountInBaseUnits, shouldCheckTransfer);
|
||||
await zeroEx.exchange.fillOrderAsync(
|
||||
signedOrder, fillTakerAmountInBaseUnits, shouldCheckTransfer, takerAddress,
|
||||
);
|
||||
})();
|
||||
});
|
||||
});
|
||||
|
@ -54,19 +54,13 @@ export class FillScenarios {
|
||||
public async createPartiallyFilledSignedOrderAsync(makerTokenAddress: string, takerTokenAddress: string,
|
||||
takerAddress: string, fillableAmount: BigNumber.BigNumber,
|
||||
partialFillAmount: BigNumber.BigNumber) {
|
||||
const prevSenderAccount = await this.zeroEx.getTransactionSenderAccountIfExistsAsync();
|
||||
const [makerAddress] = this.userAddresses;
|
||||
const signedOrder = await this.createAsymmetricFillableSignedOrderAsync(
|
||||
makerTokenAddress, takerTokenAddress, makerAddress, takerAddress,
|
||||
fillableAmount, fillableAmount,
|
||||
);
|
||||
|
||||
this.zeroEx.setTransactionSenderAccount(takerAddress);
|
||||
const shouldCheckTransfer = false;
|
||||
await this.zeroEx.exchange.fillOrderAsync(signedOrder, partialFillAmount, shouldCheckTransfer);
|
||||
|
||||
// Re-set sender account so as to avoid introducing side-effects
|
||||
this.zeroEx.setTransactionSenderAccount(prevSenderAccount as string);
|
||||
await this.zeroEx.exchange.fillOrderAsync(signedOrder, partialFillAmount, shouldCheckTransfer, takerAddress);
|
||||
return signedOrder;
|
||||
}
|
||||
private async createAsymmetricFillableSignedOrderWithFeesAsync(
|
||||
@ -89,14 +83,10 @@ export class FillScenarios {
|
||||
await this.zeroEx.token.setProxyAllowanceAsync(this.zrxTokenAddress, takerAddress, takerFee);
|
||||
}
|
||||
|
||||
const prevTransactionSenderAccount = await this.zeroEx.getTransactionSenderAccountIfExistsAsync();
|
||||
this.zeroEx.setTransactionSenderAccount(makerAddress);
|
||||
const signedOrder = await orderFactory.createSignedOrderAsync(this.zeroEx,
|
||||
makerAddress, takerAddress, makerFee, takerFee,
|
||||
makerFillableAmount, makerTokenAddress, takerFillableAmount, takerTokenAddress,
|
||||
feeRecepient, expirationUnixTimestampSec);
|
||||
// We re-set the transactionSender to avoid introducing side-effects
|
||||
this.zeroEx.setTransactionSenderAccount(prevTransactionSenderAccount as string);
|
||||
return signedOrder;
|
||||
}
|
||||
}
|
||||
|
@ -36,7 +36,7 @@ export const orderFactory = {
|
||||
expirationUnixTimestampSec,
|
||||
};
|
||||
const orderHash = await zeroEx.getOrderHashHexAsync(order);
|
||||
const ecSignature = await zeroEx.signOrderHashAsync(orderHash);
|
||||
const ecSignature = await zeroEx.signOrderHashAsync(orderHash, maker);
|
||||
const signedOrder: SignedOrder = _.assign(order, {ecSignature});
|
||||
return signedOrder;
|
||||
},
|
||||
|
Loading…
x
Reference in New Issue
Block a user