diff options
-rw-r--r-- | packages/order-utils/src/constants.ts | 10 | ||||
-rw-r--r-- | packages/order-utils/src/eip712_utils.ts | 47 | ||||
-rw-r--r-- | packages/order-utils/src/index.ts | 10 | ||||
-rw-r--r-- | packages/order-utils/src/order_hash.ts | 1 | ||||
-rw-r--r-- | packages/order-utils/test/eip712_utils_test.ts | 41 | ||||
-rw-r--r-- | packages/types/src/index.ts | 6 |
6 files changed, 88 insertions, 27 deletions
diff --git a/packages/order-utils/src/constants.ts b/packages/order-utils/src/constants.ts index a9a687719..3c93575b3 100644 --- a/packages/order-utils/src/constants.ts +++ b/packages/order-utils/src/constants.ts @@ -68,9 +68,9 @@ export const constants = { SELECTOR_CHAR_LENGTH_WITH_PREFIX: 10, INFINITE_TIMESTAMP_SEC: new BigNumber(2524604400), // Close to infinite ZERO_AMOUNT: new BigNumber(0), - EIP712_DOMAIN_NAME: '0x Protocol', - EIP712_DOMAIN_VERSION: '2', - EIP712_DOMAIN_SCHEMA: { + EXCHANGE_DOMAIN_NAME: '0x Protocol', + EXCHANGE_DOMAIN_VERSION: '2', + DEFAULT_DOMAIN_SCHEMA: { name: 'EIP712Domain', parameters: [ { name: 'name', type: 'string' }, @@ -78,7 +78,7 @@ export const constants = { { name: 'verifyingContract', type: 'address' }, ], }, - EIP712_ORDER_SCHEMA: { + EXCHANGE_ORDER_SCHEMA: { name: 'Order', parameters: [ { name: 'makerAddress', type: 'address' }, @@ -95,7 +95,7 @@ export const constants = { { name: 'takerAssetData', type: 'bytes' }, ], }, - EIP712_ZEROEX_TRANSACTION_SCHEMA: { + EXCHANGE_ZEROEX_TRANSACTION_SCHEMA: { name: 'ZeroExTransaction', parameters: [ { name: 'salt', type: 'uint256' }, diff --git a/packages/order-utils/src/eip712_utils.ts b/packages/order-utils/src/eip712_utils.ts index 4b37dba41..313653c63 100644 --- a/packages/order-utils/src/eip712_utils.ts +++ b/packages/order-utils/src/eip712_utils.ts @@ -1,36 +1,49 @@ import { assert } from '@0x/assert'; import { schemas } from '@0x/json-schemas'; -import { EIP712Object, EIP712TypedData, EIP712Types, Order, ZeroExTransaction } from '@0x/types'; +import { + EIP712DomainWithDefaultSchema, + EIP712Object, + EIP712TypedData, + EIP712Types, + Order, + ZeroExTransaction, +} from '@0x/types'; import * as _ from 'lodash'; import { constants } from './constants'; +export const DEFAULT_DOMAIN_SCHEMA = constants.DEFAULT_DOMAIN_SCHEMA; +export const EXCHANGE_DOMAIN_NAME = constants.EXCHANGE_DOMAIN_NAME; +export const EXCHANGE_DOMAIN_VERSION = constants.EXCHANGE_DOMAIN_VERSION; +export const EXCHANGE_ORDER_SCHEMA = constants.EXCHANGE_ORDER_SCHEMA; +export const EXCHANGE_ZEROEX_TRANSACTION_SCHEMA = constants.EXCHANGE_ZEROEX_TRANSACTION_SCHEMA; + export const eip712Utils = { /** * Creates a EIP712TypedData object specific to the 0x protocol for use with signTypedData. * @param primaryType The primary type found in message * @param types The additional types for the data in message * @param message The contents of the message - * @param verifyingContractAddress The address of the verifying contract + * @param domain Domain containing a name (optional), version (optional), and verifying contract address * @return A typed data object */ createTypedData: ( primaryType: string, types: EIP712Types, message: EIP712Object, - verifyingContractAddress: string, + domain: EIP712DomainWithDefaultSchema, ): EIP712TypedData => { - assert.isETHAddressHex('verifyingContractAddress', verifyingContractAddress); + assert.isETHAddressHex('verifyingContractAddress', domain.verifyingContractAddress); assert.isString('primaryType', primaryType); const typedData = { types: { - EIP712Domain: constants.EIP712_DOMAIN_SCHEMA.parameters, + EIP712Domain: DEFAULT_DOMAIN_SCHEMA.parameters, ...types, }, domain: { - name: constants.EIP712_DOMAIN_NAME, - version: constants.EIP712_DOMAIN_VERSION, - verifyingContract: verifyingContractAddress, + name: _.isUndefined(domain.name) ? EXCHANGE_DOMAIN_NAME : domain.name, + version: _.isUndefined(domain.version) ? EXCHANGE_DOMAIN_VERSION : domain.version, + verifyingContract: domain.verifyingContractAddress, }, message, primaryType, @@ -48,11 +61,14 @@ export const eip712Utils = { const normalizedOrder = _.mapValues(order, value => { return !_.isString(value) ? value.toString() : value; }); + const domain = { + verifyingContractAddress: order.exchangeAddress, + }; const typedData = eip712Utils.createTypedData( - constants.EIP712_ORDER_SCHEMA.name, - { Order: constants.EIP712_ORDER_SCHEMA.parameters }, + EXCHANGE_ORDER_SCHEMA.name, + { Order: EXCHANGE_ORDER_SCHEMA.parameters }, normalizedOrder, - order.exchangeAddress, + domain, ); return typedData; }, @@ -68,11 +84,14 @@ export const eip712Utils = { const normalizedTransaction = _.mapValues(zeroExTransaction, value => { return !_.isString(value) ? value.toString() : value; }); + const domain = { + verifyingContractAddress: zeroExTransaction.verifyingContractAddress, + }; const typedData = eip712Utils.createTypedData( - constants.EIP712_ZEROEX_TRANSACTION_SCHEMA.name, - { ZeroExTransaction: constants.EIP712_ZEROEX_TRANSACTION_SCHEMA.parameters }, + EXCHANGE_ZEROEX_TRANSACTION_SCHEMA.name, + { ZeroExTransaction: EXCHANGE_ZEROEX_TRANSACTION_SCHEMA.parameters }, normalizedTransaction, - zeroExTransaction.verifyingContractAddress, + domain, ); return typedData; }, diff --git a/packages/order-utils/src/index.ts b/packages/order-utils/src/index.ts index 26cbf9665..436677efc 100644 --- a/packages/order-utils/src/index.ts +++ b/packages/order-utils/src/index.ts @@ -19,7 +19,14 @@ export { ExchangeTransferSimulator } from './exchange_transfer_simulator'; export { BalanceAndProxyAllowanceLazyStore } from './store/balance_and_proxy_allowance_lazy_store'; export { OrderFilledCancelledLazyStore } from './store/order_filled_cancelled_lazy_store'; -export { eip712Utils } from './eip712_utils'; +export { + eip712Utils, + DEFAULT_DOMAIN_SCHEMA, + EXCHANGE_DOMAIN_NAME, + EXCHANGE_DOMAIN_VERSION, + EXCHANGE_ORDER_SCHEMA, + EXCHANGE_ZEROEX_TRANSACTION_SCHEMA, +} from './eip712_utils'; export { Provider, @@ -51,6 +58,7 @@ export { EIP712Types, EIP712Object, EIP712ObjectValue, + EIP712DomainWithDefaultSchema, ZeroExTransaction, SignedZeroExTransaction, } from '@0x/types'; diff --git a/packages/order-utils/src/order_hash.ts b/packages/order-utils/src/order_hash.ts index b15ccacf7..3bc23c14e 100644 --- a/packages/order-utils/src/order_hash.ts +++ b/packages/order-utils/src/order_hash.ts @@ -61,7 +61,6 @@ export const orderHashUtils = { } throw error; } - const typedData = eip712Utils.createOrderTypedData(order); const orderHashBuff = signTypedDataUtils.generateTypedDataHash(typedData); return orderHashBuff; diff --git a/packages/order-utils/test/eip712_utils_test.ts b/packages/order-utils/test/eip712_utils_test.ts index fb9388fcc..4208e9beb 100644 --- a/packages/order-utils/test/eip712_utils_test.ts +++ b/packages/order-utils/test/eip712_utils_test.ts @@ -3,7 +3,12 @@ import * as chai from 'chai'; import 'mocha'; import { constants } from '../src/constants'; -import { eip712Utils } from '../src/eip712_utils'; +import { + eip712Utils, + EXCHANGE_DOMAIN_NAME, + EXCHANGE_DOMAIN_VERSION, + EXCHANGE_ZEROEX_TRANSACTION_SCHEMA, +} from '../src/eip712_utils'; import { chaiSetup } from './utils/chai_setup'; @@ -12,22 +17,42 @@ const expect = chai.expect; describe('EIP712 Utils', () => { describe('createTypedData', () => { - it('adds in the EIP712DomainSeparator', () => { + it('adds in the EIP712DomainSeparator with default values', () => { + const primaryType = 'Test'; + const typedData = eip712Utils.createTypedData( + primaryType, + { Test: [{ name: 'testValue', type: 'uint256' }] }, + { testValue: '1' }, + { verifyingContractAddress: constants.NULL_ADDRESS }, + ); + expect(typedData.domain).to.not.be.undefined(); + expect(typedData.types.EIP712Domain).to.not.be.undefined(); + const domainObject = typedData.domain; + expect(domainObject.name).to.eq(EXCHANGE_DOMAIN_NAME); + expect(domainObject.version).to.eq(EXCHANGE_DOMAIN_VERSION); + expect(domainObject.verifyingContract).to.eq(constants.NULL_ADDRESS); + expect(typedData.primaryType).to.eq(primaryType); + }); + it('adds in the EIP712DomainSeparator without default values', () => { const primaryType = 'Test'; + const domainName = 'testDomain'; + const domainVersion = 'testVersion'; const typedData = eip712Utils.createTypedData( primaryType, { Test: [{ name: 'testValue', type: 'uint256' }] }, { testValue: '1' }, - constants.NULL_ADDRESS, + { name: domainName, version: domainVersion, verifyingContractAddress: constants.NULL_ADDRESS }, ); expect(typedData.domain).to.not.be.undefined(); expect(typedData.types.EIP712Domain).to.not.be.undefined(); const domainObject = typedData.domain; - expect(domainObject.name).to.eq(constants.EIP712_DOMAIN_NAME); + expect(domainObject.name).to.eq(domainName); + expect(domainObject.version).to.eq(domainVersion); + expect(domainObject.verifyingContract).to.eq(constants.NULL_ADDRESS); expect(typedData.primaryType).to.eq(primaryType); }); }); - describe('createTypedData', () => { + describe('createZeroExTransactionTypedData', () => { it('adds in the EIP712DomainSeparator', () => { const typedData = eip712Utils.createZeroExTransactionTypedData({ salt: new BigNumber('0'), @@ -35,8 +60,12 @@ describe('EIP712 Utils', () => { signerAddress: constants.NULL_ADDRESS, verifyingContractAddress: constants.NULL_ADDRESS, }); - expect(typedData.primaryType).to.eq(constants.EIP712_ZEROEX_TRANSACTION_SCHEMA.name); + expect(typedData.primaryType).to.eq(EXCHANGE_ZEROEX_TRANSACTION_SCHEMA.name); expect(typedData.types.EIP712Domain).to.not.be.undefined(); + const domainObject = typedData.domain; + expect(domainObject.name).to.eq(EXCHANGE_DOMAIN_NAME); + expect(domainObject.version).to.eq(EXCHANGE_DOMAIN_VERSION); + expect(domainObject.verifyingContract).to.eq(constants.NULL_ADDRESS); }); }); }); diff --git a/packages/types/src/index.ts b/packages/types/src/index.ts index ce124e289..a30a0494f 100644 --- a/packages/types/src/index.ts +++ b/packages/types/src/index.ts @@ -690,3 +690,9 @@ export interface DutchAuctionDetails { currentAmount: BigNumber; currentTimeSeconds: BigNumber; } + +export interface EIP712DomainWithDefaultSchema { + name?: string; + version?: string; + verifyingContractAddress: string; +} |