Compare commits
251 Commits
contracts@
...
@0xproject
Author | SHA1 | Date | |
---|---|---|---|
|
29f6adc2ed | ||
|
5446de6308 | ||
|
9540db2aad | ||
|
7dd28d6fab | ||
|
ba59879e7f | ||
|
c10807c4e3 | ||
|
4e8ec2359d | ||
|
cbd72b6e3d | ||
|
90e28220fa | ||
|
abd308455a | ||
|
3e70ab015b | ||
|
dab7f1a739 | ||
|
f6438725eb | ||
|
83ffbd05be | ||
|
88be6b5e0d | ||
|
aa47f85f48 | ||
|
fec9c8f1c6 | ||
|
e2559798df | ||
|
ccc18620bf | ||
|
febe00db4f | ||
|
6f36048a8e | ||
|
2457ecb7e7 | ||
|
2378747570 | ||
|
2df569b727 | ||
|
65aecc0024 | ||
|
074082ec94 | ||
|
6b9f0af828 | ||
|
bfabf765e3 | ||
|
e74f736eff | ||
|
45483557a5 | ||
|
07942a7aec | ||
|
3d1b7c10e8 | ||
|
cf46d2c704 | ||
|
4434856add | ||
|
52d511df21 | ||
|
50f58f9121 | ||
|
7a20c7b946 | ||
|
ce0e60ed84 | ||
|
4ad0a6c7b7 | ||
|
b8d8651e43 | ||
|
45b68832aa | ||
|
6dfcaaf889 | ||
|
8131c5d6bc | ||
|
df5779b6d1 | ||
|
4a5a0c8c78 | ||
|
b3a17624c8 | ||
|
e63841a604 | ||
|
7ec95e8c29 | ||
|
b217495465 | ||
|
db6ddc0c4b | ||
|
174b360593 | ||
|
481a752e70 | ||
|
38acdfd632 | ||
|
561e525778 | ||
|
69eb820d0d | ||
|
447f16fc4f | ||
|
1769609245 | ||
|
e1dcdac1bb | ||
|
9d45d19c80 | ||
|
9858bb0ce4 | ||
|
a3527a77a6 | ||
|
33a45fa739 | ||
|
e70882a657 | ||
|
e456332da7 | ||
|
4ed84c5dc5 | ||
|
2fe3f40be9 | ||
|
44bfdb718f | ||
|
3524efc41c | ||
|
01210c291c | ||
|
192d4b4dbf | ||
|
68246fc335 | ||
|
7ef86636aa | ||
|
a5859c6cee | ||
|
3463903d02 | ||
|
4b0f1a8431 | ||
|
603e8aa671 | ||
|
6eb980abe2 | ||
|
46b168e10f | ||
|
508e6ccf89 | ||
|
a173c5fc38 | ||
|
f5237f7971 | ||
|
6f7a5d00e6 | ||
|
4061723863 | ||
|
ab1b52ba87 | ||
|
16e94ecb40 | ||
|
6bb2c5877c | ||
|
a14450f367 | ||
|
85df313a7a | ||
|
66ed6b9b88 | ||
|
9304d09da6 | ||
|
e61dbbb6cf | ||
|
1690f59857 | ||
|
c916dd6ebb | ||
|
8a683b8541 | ||
|
4883b8be10 | ||
|
51760f9bdd | ||
|
6a619a4084 | ||
|
feeafa193a | ||
|
8d8528996a | ||
|
965d609829 | ||
|
a52714bcf3 | ||
|
bbfd7647a8 | ||
|
0aba5a3be4 | ||
|
61bf5864a8 | ||
|
56847a53f4 | ||
|
8324ab3af7 | ||
|
d496a7585c | ||
|
8d7f2a993a | ||
|
ed786f3e8f | ||
|
539c243733 | ||
|
40e0c829b3 | ||
|
e34b1f2f8b | ||
|
f6b6619c08 | ||
|
e480e08aa4 | ||
|
652cf7a976 | ||
|
7a8ab6fbe8 | ||
|
9deec8ec35 | ||
|
3f1586045c | ||
|
ada5563b1f | ||
|
6b41a570a5 | ||
|
cebf6bfb34 | ||
|
47a1b48ad8 | ||
|
ef82a9d2a6 | ||
|
ba6351841d | ||
|
cdc786a1e3 | ||
|
3ea137a78f | ||
|
b525ccc825 | ||
|
77acbdd3ea | ||
|
c13190ceab | ||
|
78d4fc59a5 | ||
|
f9e86c057d | ||
|
1d8e133a30 | ||
|
99fbf384fd | ||
|
cb4fcf4de7 | ||
|
675964dc5c | ||
|
6432f85eb0 | ||
|
66eef758c6 | ||
|
c64f0ba34b | ||
|
6deffb6b28 | ||
|
5802713801 | ||
|
11df29fa8e | ||
|
f4a41e80b8 | ||
|
5c655b55d3 | ||
|
63c15b6f4f | ||
|
4f2bc29744 | ||
|
2cac431c41 | ||
|
80b7a7842c | ||
|
8c7cec9822 | ||
|
971a4087d2 | ||
|
660e670d38 | ||
|
052824f4e3 | ||
|
1d5ef4d0ca | ||
|
a6440b94f4 | ||
|
01685b7622 | ||
|
397fefa8d7 | ||
|
82a01ef020 | ||
|
a224ce347e | ||
|
81ba2a8411 | ||
|
a6e8b28da5 | ||
|
e90dbf66f3 | ||
|
0be2219beb | ||
|
09b4d5e0e4 | ||
|
60f1bcf51f | ||
|
431ac3b401 | ||
|
50781bd77a | ||
|
c3361bb86e | ||
|
fd5ad69c26 | ||
|
b1f97a27f3 | ||
|
febddcb356 | ||
|
74d5af34eb | ||
|
365890291f | ||
|
0368de701f | ||
|
f5e7b7e7e0 | ||
|
038c21324e | ||
|
5d008ee83e | ||
|
d0f6933980 | ||
|
14793f30b5 | ||
|
86319291e3 | ||
|
afa2dd7374 | ||
|
1312e4caf2 | ||
|
eb4517d737 | ||
|
d80701c277 | ||
|
bf3ab1127d | ||
|
dcb12b6ad6 | ||
|
f87420a776 | ||
|
6cedf5362b | ||
|
aa833ef074 | ||
|
5f1c9cfee5 | ||
|
62b93cf2eb | ||
|
b1c5f6e8f1 | ||
|
3bc9b309f6 | ||
|
6924a2b681 | ||
|
d93d4c34f5 | ||
|
557267477e | ||
|
b9f7979e91 | ||
|
8c803ab232 | ||
|
422e5e4dd7 | ||
|
2aea820d89 | ||
|
1c3b2b7141 | ||
|
e7d5ceb9c5 | ||
|
68af0e9eb7 | ||
|
a18d0f6229 | ||
|
031807df9c | ||
|
72710be04b | ||
|
ac135d55d3 | ||
|
1d55e94659 | ||
|
86284f1c7e | ||
|
61a4ae7fc4 | ||
|
55fab3d98f | ||
|
de11b62e30 | ||
|
8e14e65b60 | ||
|
2d1d14d2e4 | ||
|
f44644ad90 | ||
|
ac1640140c | ||
|
1402a0aa22 | ||
|
f225f9e7c8 | ||
|
14fdb71a71 | ||
|
9c4c4fb19a | ||
|
5785ec0713 | ||
|
2eab0e30b7 | ||
|
2c846ff145 | ||
|
ca0dfc6610 | ||
|
0fd44ee2c1 | ||
|
7271fc0bab | ||
|
6c039bbeb1 | ||
|
38e6d26145 | ||
|
b0f210dea9 | ||
|
f7469080f9 | ||
|
fb5ea5d99f | ||
|
be2f4cbdca | ||
|
68f2dc11b4 | ||
|
d6c670dfcb | ||
|
0736c41357 | ||
|
898bd75a18 | ||
|
260313a6ae | ||
|
6a99bfa68e | ||
|
f60adbdd72 | ||
|
1be310cef4 | ||
|
ff4f86f1d6 | ||
|
f4a4fefe42 | ||
|
91a9014a50 | ||
|
ad161a973e | ||
|
103e1aa250 | ||
|
641d86cb98 | ||
|
813b2ca1fb | ||
|
ec96c3bb77 | ||
|
65120e84e2 | ||
|
374ee2db32 | ||
|
48ab151ec2 | ||
|
44a430802e | ||
|
6b03cfd40d |
@@ -2,6 +2,7 @@ version: 2
|
||||
|
||||
jobs:
|
||||
build:
|
||||
resource_class: medium+
|
||||
docker:
|
||||
- image: circleci/node:9
|
||||
environment:
|
||||
@@ -60,6 +61,7 @@ jobs:
|
||||
# initialized
|
||||
- run: sleep 10 && TEST_PROVIDER=geth yarn wsrun test contracts
|
||||
test-publish:
|
||||
resource_class: medium+
|
||||
docker:
|
||||
- image: circleci/node:9
|
||||
- image: verdaccio/verdaccio
|
||||
|
5
.gitignore
vendored
5
.gitignore
vendored
@@ -88,7 +88,7 @@ packages/0x.js/src/artifacts/
|
||||
packages/order-utils/src/artifacts/
|
||||
|
||||
# unstable generated contract artifacts:
|
||||
packages/migrations/artifacts/2.0.0/
|
||||
packages/migrations/artifacts/development/
|
||||
|
||||
# generated contract watcher
|
||||
packages/0x.js/src/generated_contract_wrappers/
|
||||
@@ -99,8 +99,9 @@ packages/fill-scenarios/src/generated_contract_wrappers/
|
||||
packages/order-watcher/src/generated_contract_wrappers/
|
||||
packages/order-utils/src/generated_contract_wrappers/
|
||||
packages/migrations/src/1.0.0/contract_wrappers
|
||||
packages/migrations/src/2.0.0-testnet/contract_wrappers
|
||||
packages/migrations/src/2.0.0/contract_wrappers
|
||||
packages/migrations/src/2.0.0-beta-testnet/contract_wrappers
|
||||
packages/migrations/src/development/contract_wrappers
|
||||
|
||||
# solc-bin in sol-compiler
|
||||
packages/sol-compiler/solc_bin/
|
||||
|
@@ -8,8 +8,8 @@ lib
|
||||
/packages/order-watcher/src/generated_contract_wrappers/
|
||||
/packages/order-utils/src/generated_contract_wrappers/
|
||||
/packages/migrations/src/1.0.0/contract_wrappers
|
||||
/packages/migrations/src/2.0.0-testnet/contract_wrappers
|
||||
/packages/migrations/src/2.0.0/contract_wrappers
|
||||
/packages/migrations/src/2.0.0-beta-testnet/contract_wrappers
|
||||
/packages/0x.js/src/artifacts
|
||||
/packages/contracts/src/artifacts
|
||||
/packages/contract-wrappers/src/artifacts
|
||||
@@ -19,7 +19,9 @@ lib
|
||||
/packages/contract-wrappers/test/artifacts
|
||||
/packages/order-watcher/test/artifacts
|
||||
/packages/migrations/artifacts/1.0.0
|
||||
/packages/migrations/artifacts/2.0.0-testnet
|
||||
/packages/migrations/artifacts/2.0.0
|
||||
/packages/migrations/artifacts/2.0.0-beta-testnet
|
||||
/packages/migrations/artifacts/development
|
||||
package.json
|
||||
scripts/postpublish_utils.js
|
||||
packages/sol-cov/test/fixtures/artifacts
|
||||
|
@@ -23,10 +23,11 @@
|
||||
"install:all": "yarn install",
|
||||
"wsrun": "wsrun",
|
||||
"lerna": "lerna",
|
||||
"watch": "wsrun watch_without_deps $PKG --fast-exit -r --stages --done-criteria='complete|successfully'",
|
||||
"build": "wsrun build $PKG --fast-exit -r --stages",
|
||||
"build:no_website": "wsrun build $PKG --fast-exit -r --stages --exclude @0xproject/website",
|
||||
"build:monorepo_scripts": "PKG=@0xproject/monorepo-scripts yarn build",
|
||||
"build:ts": "tsc -b",
|
||||
"watch:ts": "tsc -b -w",
|
||||
"clean": "wsrun clean $PKG --fast-exit -r --parallel",
|
||||
"remove_node_modules": "lerna clean --yes; rm -rf node_modules",
|
||||
"rebuild": "run-s clean build",
|
||||
@@ -51,6 +52,7 @@
|
||||
"npm-run-all": "^4.1.2",
|
||||
"prettier": "^1.11.1",
|
||||
"source-map-support": "^0.5.6",
|
||||
"typescript": "3.0.1",
|
||||
"wsrun": "^2.2.0"
|
||||
},
|
||||
"resolutions": {
|
||||
|
@@ -1,4 +1,40 @@
|
||||
[
|
||||
{
|
||||
"timestamp": 1537541580,
|
||||
"version": "1.0.4",
|
||||
"changes": [
|
||||
{
|
||||
"note": "Dependencies updated"
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"version": "1.0.3",
|
||||
"changes": [
|
||||
{
|
||||
"note": "Drastically reduce the bundle size by removing unused parts of included contract artifacts."
|
||||
}
|
||||
],
|
||||
"timestamp": 1537369748
|
||||
},
|
||||
{
|
||||
"version": "1.0.2",
|
||||
"changes": [
|
||||
{
|
||||
"note": "Add ZRX & WETH mainnet contract addresses into the included artifacts"
|
||||
}
|
||||
],
|
||||
"timestamp": 1537265493
|
||||
},
|
||||
{
|
||||
"timestamp": 1536142250,
|
||||
"version": "1.0.1",
|
||||
"changes": [
|
||||
{
|
||||
"note": "Dependencies updated"
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"version": "1.0.1-rc.6",
|
||||
"changes": [
|
||||
|
@@ -5,6 +5,22 @@ Edit the package's CHANGELOG.json file only.
|
||||
|
||||
CHANGELOG
|
||||
|
||||
## v1.0.4 - _September 21, 2018_
|
||||
|
||||
* Dependencies updated
|
||||
|
||||
## v1.0.3 - _September 19, 2018_
|
||||
|
||||
* Drastically reduce the bundle size by removing unused parts of included contract artifacts.
|
||||
|
||||
## v1.0.2 - _September 18, 2018_
|
||||
|
||||
* Add ZRX & WETH mainnet contract addresses into the included artifacts
|
||||
|
||||
## v1.0.1 - _September 5, 2018_
|
||||
|
||||
* Dependencies updated
|
||||
|
||||
## v1.0.1-rc.6 - _August 27, 2018_
|
||||
|
||||
* Fix missing `BlockParamLiteral` type import issue
|
||||
|
@@ -1,6 +1,6 @@
|
||||
## 0x.js
|
||||
|
||||
A TypeScript/Javascript library for interacting with the 0x protocol.
|
||||
A TypeScript/Javascript library for interacting with the 0x protocol. It is a high level package which combines a number of underlying packages such as order-utils and order-watcher.
|
||||
|
||||
### Read the [Documentation](https://0xproject.com/docs/0x.js).
|
||||
|
||||
@@ -19,7 +19,14 @@ npm install 0x.js --save
|
||||
**Import**
|
||||
|
||||
```javascript
|
||||
import { ZeroEx } from '0x.js';
|
||||
import {
|
||||
assetDataUtils,
|
||||
BigNumber,
|
||||
ContractWrappers,
|
||||
generatePseudoRandomSalt,
|
||||
orderHashUtils,
|
||||
signatureUtils,
|
||||
} from '0x.js';
|
||||
```
|
||||
|
||||
If your project is in [TypeScript](https://www.typescriptlang.org/), add the following to your `tsconfig.json`:
|
||||
|
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "0x.js",
|
||||
"version": "1.0.1-rc.6",
|
||||
"version": "1.0.4",
|
||||
"engines": {
|
||||
"node": ">=6.12"
|
||||
},
|
||||
@@ -15,7 +15,6 @@
|
||||
"main": "lib/index.js",
|
||||
"types": "lib/index.d.ts",
|
||||
"scripts": {
|
||||
"watch_without_deps": "tsc -w",
|
||||
"build": "yarn build:all",
|
||||
"build:all": "run-p build:umd:prod build:commonjs",
|
||||
"lint": "tslint --project . --exclude **/src/generated_contract_wrappers/**/*",
|
||||
@@ -25,8 +24,8 @@
|
||||
"coverage:report:lcov": "nyc report --reporter=text-lcov > coverage/lcov.info",
|
||||
"clean": "shx rm -rf _bundles lib test_temp src/generated_contract_wrappers generated_docs",
|
||||
"build:umd:prod": "NODE_ENV=production webpack",
|
||||
"build:commonjs": "tsc",
|
||||
"docs:json": "typedoc --excludePrivate --excludeExternals --target ES5 --json $JSON_FILE_PATH $PROJECT_FILES"
|
||||
"build:commonjs": "tsc -b",
|
||||
"docs:json": "typedoc --excludePrivate --excludeExternals --target ES5 --tsconfig typedoc-tsconfig.json --json $JSON_FILE_PATH $PROJECT_FILES"
|
||||
},
|
||||
"config": {
|
||||
"postpublish": {
|
||||
@@ -42,15 +41,16 @@
|
||||
},
|
||||
"license": "Apache-2.0",
|
||||
"devDependencies": {
|
||||
"@0xproject/abi-gen": "^1.0.7",
|
||||
"@0xproject/dev-utils": "^1.0.6",
|
||||
"@0xproject/migrations": "^1.0.6",
|
||||
"@0xproject/monorepo-scripts": "^1.0.7",
|
||||
"@0xproject/tslint-config": "^1.0.6",
|
||||
"@0xproject/abi-gen": "^1.0.9",
|
||||
"@0xproject/dev-utils": "^1.0.8",
|
||||
"@0xproject/migrations": "^1.0.10",
|
||||
"@0xproject/monorepo-scripts": "^1.0.9",
|
||||
"@0xproject/tslint-config": "^1.0.7",
|
||||
"@types/lodash": "4.14.104",
|
||||
"@types/mocha": "^2.2.42",
|
||||
"@types/node": "^8.0.53",
|
||||
"@types/node": "*",
|
||||
"@types/sinon": "^2.2.2",
|
||||
"@types/web3-provider-engine": "^14.0.0",
|
||||
"awesome-typescript-loader": "^3.1.3",
|
||||
"chai": "^4.0.1",
|
||||
"chai-as-promised": "^7.1.0",
|
||||
@@ -73,17 +73,17 @@
|
||||
"webpack": "^3.1.0"
|
||||
},
|
||||
"dependencies": {
|
||||
"@0xproject/assert": "^1.0.7",
|
||||
"@0xproject/base-contract": "^2.0.1",
|
||||
"@0xproject/contract-wrappers": "^1.0.1-rc.5",
|
||||
"@0xproject/order-utils": "^1.0.1-rc.6",
|
||||
"@0xproject/order-watcher": "^1.0.1-rc.5",
|
||||
"@0xproject/subproviders": "^2.0.1",
|
||||
"@0xproject/types": "^1.0.1-rc.6",
|
||||
"@0xproject/typescript-typings": "^1.0.5",
|
||||
"@0xproject/utils": "^1.0.7",
|
||||
"@0xproject/web3-wrapper": "^2.0.1",
|
||||
"ethereum-types": "^1.0.5",
|
||||
"@0xproject/assert": "^1.0.9",
|
||||
"@0xproject/base-contract": "^2.0.3",
|
||||
"@0xproject/contract-wrappers": "^1.0.4",
|
||||
"@0xproject/order-utils": "^1.0.3",
|
||||
"@0xproject/order-watcher": "^1.0.4",
|
||||
"@0xproject/subproviders": "^2.0.3",
|
||||
"@0xproject/types": "^1.0.2",
|
||||
"@0xproject/typescript-typings": "^2.0.1",
|
||||
"@0xproject/utils": "^1.0.9",
|
||||
"@0xproject/web3-wrapper": "^2.0.3",
|
||||
"ethereum-types": "^1.0.7",
|
||||
"ethers": "3.0.22",
|
||||
"lodash": "^4.17.5",
|
||||
"web3-provider-engine": "14.0.6"
|
||||
|
@@ -9,6 +9,7 @@ export {
|
||||
ERC20ProxyWrapper,
|
||||
ERC721ProxyWrapper,
|
||||
ForwarderWrapper,
|
||||
OrderValidatorWrapper,
|
||||
IndexedFilterValues,
|
||||
BlockRange,
|
||||
ContractWrappersConfig,
|
||||
@@ -42,6 +43,10 @@ export {
|
||||
DecodedLogEvent,
|
||||
ExchangeEventArgs,
|
||||
TransactionEncoder,
|
||||
BalanceAndAllowance,
|
||||
OrderAndTraderInfo,
|
||||
TraderInfo,
|
||||
ValidateOrderFillableOpts,
|
||||
} from '@0xproject/contract-wrappers';
|
||||
|
||||
export { OrderWatcher, OnOrderStateChangeCallback, OrderWatcherConfig } from '@0xproject/order-watcher';
|
||||
|
@@ -1,7 +1,8 @@
|
||||
{
|
||||
"extends": "../../tsconfig",
|
||||
"compilerOptions": {
|
||||
"outDir": "lib"
|
||||
"outDir": "lib",
|
||||
"rootDir": "src"
|
||||
},
|
||||
"include": ["./src/**/*", "./test/**/*"]
|
||||
"include": ["./src/**/*"]
|
||||
}
|
||||
|
7
packages/0x.js/typedoc-tsconfig.json
Normal file
7
packages/0x.js/typedoc-tsconfig.json
Normal file
@@ -0,0 +1,7 @@
|
||||
{
|
||||
"extends": "../../typedoc-tsconfig",
|
||||
"compilerOptions": {
|
||||
"outDir": "lib"
|
||||
},
|
||||
"include": ["./src/**/*", "./test/**/*"]
|
||||
}
|
@@ -47,8 +47,13 @@ module.exports = {
|
||||
use: [
|
||||
{
|
||||
loader: 'awesome-typescript-loader',
|
||||
// tsconfig.json contains some options required for
|
||||
// project references which do not work with webback.
|
||||
// We override those options here.
|
||||
query: {
|
||||
declaration: false,
|
||||
declarationMap: false,
|
||||
composite: false,
|
||||
},
|
||||
},
|
||||
],
|
||||
|
@@ -1,4 +1,22 @@
|
||||
[
|
||||
{
|
||||
"timestamp": 1537541580,
|
||||
"version": "1.0.9",
|
||||
"changes": [
|
||||
{
|
||||
"note": "Dependencies updated"
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"timestamp": 1536142250,
|
||||
"version": "1.0.8",
|
||||
"changes": [
|
||||
{
|
||||
"note": "Dependencies updated"
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"timestamp": 1535377027,
|
||||
"version": "1.0.7",
|
||||
|
@@ -5,6 +5,14 @@ Edit the package's CHANGELOG.json file only.
|
||||
|
||||
CHANGELOG
|
||||
|
||||
## v1.0.9 - _September 21, 2018_
|
||||
|
||||
* Dependencies updated
|
||||
|
||||
## v1.0.8 - _September 5, 2018_
|
||||
|
||||
* Dependencies updated
|
||||
|
||||
## v1.0.7 - _August 27, 2018_
|
||||
|
||||
* Dependencies updated
|
||||
|
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@0xproject/abi-gen",
|
||||
"version": "1.0.7",
|
||||
"version": "1.0.9",
|
||||
"engines": {
|
||||
"node": ">=6.12"
|
||||
},
|
||||
@@ -8,10 +8,9 @@
|
||||
"main": "lib/src/index.js",
|
||||
"types": "lib/src/index.d.ts",
|
||||
"scripts": {
|
||||
"watch_without_deps": "tsc -w",
|
||||
"lint": "tslint --project .",
|
||||
"clean": "shx rm -rf lib",
|
||||
"build": "tsc",
|
||||
"build": "tsc -b",
|
||||
"test": "yarn run_mocha",
|
||||
"run_mocha": "mocha --require source-map-support/register --require make-promises-safe lib/test/**/*_test.js --bail --exit",
|
||||
"test:circleci": "yarn test:coverage",
|
||||
@@ -31,10 +30,10 @@
|
||||
},
|
||||
"homepage": "https://github.com/0xProject/0x-monorepo/packages/abi-gen/README.md",
|
||||
"dependencies": {
|
||||
"@0xproject/typescript-typings": "^1.0.5",
|
||||
"@0xproject/utils": "^1.0.7",
|
||||
"@0xproject/typescript-typings": "^2.0.1",
|
||||
"@0xproject/utils": "^1.0.9",
|
||||
"chalk": "^2.3.0",
|
||||
"ethereum-types": "^1.0.5",
|
||||
"ethereum-types": "^1.0.7",
|
||||
"glob": "^7.1.2",
|
||||
"handlebars": "^4.0.11",
|
||||
"lodash": "^4.17.5",
|
||||
@@ -45,11 +44,11 @@
|
||||
"yargs": "^10.0.3"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@0xproject/tslint-config": "^1.0.6",
|
||||
"@0xproject/tslint-config": "^1.0.7",
|
||||
"@types/glob": "5.0.35",
|
||||
"@types/handlebars": "^4.0.36",
|
||||
"@types/mkdirp": "^0.5.1",
|
||||
"@types/node": "^8.0.53",
|
||||
"@types/node": "*",
|
||||
"@types/sleep": "^0.0.7",
|
||||
"@types/tmp": "^0.0.33",
|
||||
"@types/yargs": "^10.0.0",
|
||||
|
@@ -1,7 +1,8 @@
|
||||
{
|
||||
"extends": "../../tsconfig",
|
||||
"compilerOptions": {
|
||||
"outDir": "lib"
|
||||
"outDir": "lib",
|
||||
"rootDir": "."
|
||||
},
|
||||
"include": ["./src/**/*", "./test/**/*"]
|
||||
}
|
||||
|
@@ -1,4 +1,22 @@
|
||||
[
|
||||
{
|
||||
"timestamp": 1537541580,
|
||||
"version": "1.0.9",
|
||||
"changes": [
|
||||
{
|
||||
"note": "Dependencies updated"
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"timestamp": 1536142250,
|
||||
"version": "1.0.8",
|
||||
"changes": [
|
||||
{
|
||||
"note": "Dependencies updated"
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"timestamp": 1535377027,
|
||||
"version": "1.0.7",
|
||||
|
@@ -5,6 +5,14 @@ Edit the package's CHANGELOG.json file only.
|
||||
|
||||
CHANGELOG
|
||||
|
||||
## v1.0.9 - _September 21, 2018_
|
||||
|
||||
* Dependencies updated
|
||||
|
||||
## v1.0.8 - _September 5, 2018_
|
||||
|
||||
* Dependencies updated
|
||||
|
||||
## v1.0.7 - _August 27, 2018_
|
||||
|
||||
* Dependencies updated
|
||||
|
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@0xproject/assert",
|
||||
"version": "1.0.7",
|
||||
"version": "1.0.9",
|
||||
"engines": {
|
||||
"node": ">=6.12"
|
||||
},
|
||||
@@ -8,8 +8,7 @@
|
||||
"main": "lib/src/index.js",
|
||||
"types": "lib/src/index.d.ts",
|
||||
"scripts": {
|
||||
"watch_without_deps": "tsc -w",
|
||||
"build": "tsc",
|
||||
"build": "tsc -b",
|
||||
"clean": "shx rm -rf lib test_temp",
|
||||
"lint": "tslint --project .",
|
||||
"run_mocha": "mocha --require source-map-support/register --require make-promises-safe lib/test/**/*_test.js --exit",
|
||||
@@ -29,7 +28,7 @@
|
||||
},
|
||||
"homepage": "https://github.com/0xProject/0x-monorepo/packages/assert/README.md",
|
||||
"devDependencies": {
|
||||
"@0xproject/tslint-config": "^1.0.6",
|
||||
"@0xproject/tslint-config": "^1.0.7",
|
||||
"@types/lodash": "4.14.104",
|
||||
"@types/mocha": "^2.2.42",
|
||||
"@types/valid-url": "^1.0.2",
|
||||
@@ -45,9 +44,9 @@
|
||||
"typescript": "3.0.1"
|
||||
},
|
||||
"dependencies": {
|
||||
"@0xproject/json-schemas": "^1.0.1-rc.6",
|
||||
"@0xproject/typescript-typings": "^1.0.5",
|
||||
"@0xproject/utils": "^1.0.7",
|
||||
"@0xproject/json-schemas": "^1.0.2",
|
||||
"@0xproject/typescript-typings": "^2.0.1",
|
||||
"@0xproject/utils": "^1.0.9",
|
||||
"lodash": "^4.17.5",
|
||||
"valid-url": "^1.0.9"
|
||||
},
|
||||
|
@@ -1,7 +1,8 @@
|
||||
{
|
||||
"extends": "../../tsconfig",
|
||||
"compilerOptions": {
|
||||
"outDir": "lib"
|
||||
"outDir": "lib",
|
||||
"rootDir": "."
|
||||
},
|
||||
"include": ["./src/**/*", "./test/**/*"]
|
||||
}
|
||||
|
@@ -1,4 +1,22 @@
|
||||
[
|
||||
{
|
||||
"timestamp": 1537541580,
|
||||
"version": "2.0.3",
|
||||
"changes": [
|
||||
{
|
||||
"note": "Dependencies updated"
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"timestamp": 1536142250,
|
||||
"version": "2.0.2",
|
||||
"changes": [
|
||||
{
|
||||
"note": "Dependencies updated"
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"timestamp": 1535377027,
|
||||
"version": "2.0.1",
|
||||
|
@@ -5,6 +5,14 @@ Edit the package's CHANGELOG.json file only.
|
||||
|
||||
CHANGELOG
|
||||
|
||||
## v2.0.3 - _September 21, 2018_
|
||||
|
||||
* Dependencies updated
|
||||
|
||||
## v2.0.2 - _September 5, 2018_
|
||||
|
||||
* Dependencies updated
|
||||
|
||||
## v2.0.1 - _August 27, 2018_
|
||||
|
||||
* Dependencies updated
|
||||
|
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@0xproject/base-contract",
|
||||
"version": "2.0.1",
|
||||
"version": "2.0.3",
|
||||
"engines": {
|
||||
"node": ">=6.12"
|
||||
},
|
||||
@@ -8,8 +8,7 @@
|
||||
"main": "lib/src/index.js",
|
||||
"types": "lib/src/index.d.ts",
|
||||
"scripts": {
|
||||
"watch_without_deps": "tsc -w",
|
||||
"build": "tsc",
|
||||
"build": "tsc -b",
|
||||
"clean": "shx rm -rf lib",
|
||||
"test": "yarn run_mocha",
|
||||
"rebuild_and_test": "run-s clean build test",
|
||||
@@ -29,7 +28,7 @@
|
||||
},
|
||||
"homepage": "https://github.com/0xProject/0x-monorepo/packages/base-contract/README.md",
|
||||
"devDependencies": {
|
||||
"@0xproject/tslint-config": "^1.0.6",
|
||||
"@0xproject/tslint-config": "^1.0.7",
|
||||
"@types/lodash": "4.14.104",
|
||||
"chai": "^4.0.1",
|
||||
"copyfiles": "^2.0.0",
|
||||
@@ -41,10 +40,10 @@
|
||||
"typescript": "3.0.1"
|
||||
},
|
||||
"dependencies": {
|
||||
"@0xproject/typescript-typings": "^1.0.5",
|
||||
"@0xproject/utils": "^1.0.7",
|
||||
"@0xproject/web3-wrapper": "^2.0.1",
|
||||
"ethereum-types": "^1.0.5",
|
||||
"@0xproject/typescript-typings": "^2.0.1",
|
||||
"@0xproject/utils": "^1.0.9",
|
||||
"@0xproject/web3-wrapper": "^2.0.3",
|
||||
"ethereum-types": "^1.0.7",
|
||||
"ethers": "3.0.22",
|
||||
"lodash": "^4.17.5"
|
||||
},
|
||||
|
@@ -1,7 +1,8 @@
|
||||
{
|
||||
"extends": "../../tsconfig",
|
||||
"compilerOptions": {
|
||||
"outDir": "lib"
|
||||
"outDir": "lib",
|
||||
"rootDir": "."
|
||||
},
|
||||
"include": ["src/**/*", "test/**/*"]
|
||||
}
|
||||
|
@@ -1,4 +1,32 @@
|
||||
[
|
||||
{
|
||||
"timestamp": 1537541580,
|
||||
"version": "2.0.2",
|
||||
"changes": [
|
||||
{
|
||||
"note": "Dependencies updated"
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"timestamp": 1537369748,
|
||||
"version": "2.0.1",
|
||||
"changes": [
|
||||
{
|
||||
"note": "Dependencies updated"
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"version": "2.0.0",
|
||||
"changes": [
|
||||
{
|
||||
"note": "Change `OrderConfigRequest` to use BigNumber instead of string for relevant fields.",
|
||||
"pr": 1058
|
||||
}
|
||||
],
|
||||
"timestamp": 1536142250
|
||||
},
|
||||
{
|
||||
"version": "2.0.0-rc.2",
|
||||
"changes": [
|
||||
|
@@ -5,6 +5,18 @@ Edit the package's CHANGELOG.json file only.
|
||||
|
||||
CHANGELOG
|
||||
|
||||
## v2.0.2 - _September 21, 2018_
|
||||
|
||||
* Dependencies updated
|
||||
|
||||
## v2.0.1 - _September 19, 2018_
|
||||
|
||||
* Dependencies updated
|
||||
|
||||
## v2.0.0 - _September 5, 2018_
|
||||
|
||||
* Change `OrderConfigRequest` to use BigNumber instead of string for relevant fields. (#1058)
|
||||
|
||||
## v2.0.0-rc.2 - _August 27, 2018_
|
||||
|
||||
* Dependencies updated
|
||||
|
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@0xproject/connect",
|
||||
"version": "2.0.0-rc.2",
|
||||
"version": "2.0.2",
|
||||
"engines": {
|
||||
"node": ">=6.12"
|
||||
},
|
||||
@@ -15,8 +15,7 @@
|
||||
"main": "lib/src/index.js",
|
||||
"types": "lib/src/index.d.ts",
|
||||
"scripts": {
|
||||
"watch_without_deps": "tsc -w",
|
||||
"build": "tsc",
|
||||
"build": "tsc -b",
|
||||
"clean": "shx rm -rf lib test_temp generated_docs",
|
||||
"copy_test_fixtures": "copyfiles -u 2 './test/fixtures/**/*.json' ./lib/test/fixtures",
|
||||
"lint": "tslint --project .",
|
||||
@@ -26,7 +25,7 @@
|
||||
"test:coverage": "nyc npm run test --all && yarn coverage:report:lcov",
|
||||
"coverage:report:lcov": "nyc report --reporter=text-lcov > coverage/lcov.info",
|
||||
"test:circleci": "yarn test:coverage",
|
||||
"docs:json": "typedoc --excludePrivate --excludeExternals --target ES5 --json $JSON_FILE_PATH $PROJECT_FILES"
|
||||
"docs:json": "typedoc --excludePrivate --excludeExternals --target ES5 --tsconfig typedoc-tsconfig.json --json $JSON_FILE_PATH $PROJECT_FILES"
|
||||
},
|
||||
"config": {
|
||||
"postpublish": {
|
||||
@@ -44,11 +43,12 @@
|
||||
},
|
||||
"homepage": "https://github.com/0xProject/0x-monorepo/packages/connect/README.md",
|
||||
"dependencies": {
|
||||
"@0xproject/assert": "^1.0.7",
|
||||
"@0xproject/json-schemas": "^1.0.1-rc.6",
|
||||
"@0xproject/types": "^1.0.1-rc.6",
|
||||
"@0xproject/typescript-typings": "^1.0.5",
|
||||
"@0xproject/utils": "^1.0.7",
|
||||
"@0xproject/assert": "^1.0.9",
|
||||
"@0xproject/json-schemas": "^1.0.2",
|
||||
"@0xproject/order-utils": "^1.0.3",
|
||||
"@0xproject/types": "^1.0.2",
|
||||
"@0xproject/typescript-typings": "^2.0.1",
|
||||
"@0xproject/utils": "^1.0.9",
|
||||
"lodash": "^4.17.5",
|
||||
"query-string": "^5.0.1",
|
||||
"sinon": "^4.0.0",
|
||||
@@ -56,7 +56,7 @@
|
||||
"websocket": "^1.0.25"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@0xproject/tslint-config": "^1.0.6",
|
||||
"@0xproject/tslint-config": "^1.0.7",
|
||||
"@types/fetch-mock": "^6.0.3",
|
||||
"@types/lodash": "4.14.104",
|
||||
"@types/mocha": "^2.2.42",
|
||||
|
@@ -151,7 +151,7 @@ export class HttpClient implements Client {
|
||||
params: requestOpts,
|
||||
payload: request,
|
||||
};
|
||||
const responseJson = await this._requestAsync('/order_config', HttpRequestType.Post, httpRequestOpts);
|
||||
const responseJson = await this._requestAsync('/order_config', HttpRequestType.Get, httpRequestOpts);
|
||||
const fees = relayerResponseJsonParsers.parseOrderConfigResponseJson(responseJson);
|
||||
return fees;
|
||||
}
|
||||
|
@@ -126,12 +126,12 @@ export interface PaginatedCollection<T> {
|
||||
export interface OrderConfigRequest {
|
||||
makerAddress: string;
|
||||
takerAddress: string;
|
||||
makerAssetAmount: string;
|
||||
takerAssetAmount: string;
|
||||
makerAssetAmount: BigNumber;
|
||||
takerAssetAmount: BigNumber;
|
||||
makerAssetData: string;
|
||||
takerAssetData: string;
|
||||
exchangeAddress: string;
|
||||
expirationTimeSeconds: string;
|
||||
expirationTimeSeconds: BigNumber;
|
||||
}
|
||||
|
||||
export interface OrderConfigResponse {
|
||||
|
@@ -1,5 +1,6 @@
|
||||
import { assert } from '@0xproject/assert';
|
||||
import { schemas } from '@0xproject/json-schemas';
|
||||
import { orderParsingUtils } from '@0xproject/order-utils';
|
||||
|
||||
import {
|
||||
APIOrder,
|
||||
@@ -19,7 +20,7 @@ export const relayerResponseJsonParsers = {
|
||||
},
|
||||
parseAssetPairsItemsJson(json: any): AssetPairsItem[] {
|
||||
return json.map((assetDataPair: any) => {
|
||||
return typeConverters.convertStringsFieldsToBigNumbers(assetDataPair, [
|
||||
return orderParsingUtils.convertStringsFieldsToBigNumbers(assetDataPair, [
|
||||
'assetDataA.minAmount',
|
||||
'assetDataA.maxAmount',
|
||||
'assetDataB.minAmount',
|
||||
@@ -44,6 +45,6 @@ export const relayerResponseJsonParsers = {
|
||||
},
|
||||
parseOrderConfigResponseJson(json: any): OrderConfigResponse {
|
||||
assert.doesConformToSchema('orderConfigResponse', json, schemas.relayerApiOrderConfigResponseSchema);
|
||||
return typeConverters.convertStringsFieldsToBigNumbers(json, ['makerFee', 'takerFee']);
|
||||
return orderParsingUtils.convertStringsFieldsToBigNumbers(json, ['makerFee', 'takerFee']);
|
||||
},
|
||||
};
|
||||
|
@@ -1,4 +1,4 @@
|
||||
import { BigNumber } from '@0xproject/utils';
|
||||
import { orderParsingUtils } from '@0xproject/order-utils';
|
||||
import * as _ from 'lodash';
|
||||
|
||||
import { APIOrder } from '../types';
|
||||
@@ -21,28 +21,6 @@ export const typeConverters = {
|
||||
};
|
||||
},
|
||||
convertAPIOrderStringFieldsToBigNumber(apiOrder: any): APIOrder {
|
||||
return { ...apiOrder, order: typeConverters.convertOrderStringFieldsToBigNumber(apiOrder.order) };
|
||||
},
|
||||
convertOrderStringFieldsToBigNumber(order: any): any {
|
||||
return typeConverters.convertStringsFieldsToBigNumbers(order, [
|
||||
'makerAssetAmount',
|
||||
'takerAssetAmount',
|
||||
'makerFee',
|
||||
'takerFee',
|
||||
'expirationTimeSeconds',
|
||||
'salt',
|
||||
]);
|
||||
},
|
||||
convertStringsFieldsToBigNumbers(obj: any, fields: string[]): any {
|
||||
const result = _.assign({}, obj);
|
||||
_.each(fields, field => {
|
||||
_.update(result, field, (value: string) => {
|
||||
if (_.isUndefined(value)) {
|
||||
throw new Error(`Could not find field '${field}' while converting string fields to BigNumber.`);
|
||||
}
|
||||
return new BigNumber(value);
|
||||
});
|
||||
});
|
||||
return result;
|
||||
return { ...apiOrder, order: orderParsingUtils.convertOrderStringFieldsToBigNumber(apiOrder.order) };
|
||||
},
|
||||
};
|
||||
|
@@ -1,3 +1,4 @@
|
||||
import { BigNumber } from '@0xproject/utils';
|
||||
import * as chai from 'chai';
|
||||
import * as chaiAsPromised from 'chai-as-promised';
|
||||
import * as dirtyChai from 'dirty-chai';
|
||||
@@ -138,21 +139,21 @@ describe('HttpClient', () => {
|
||||
const request = {
|
||||
makerAddress: '0x9e56625509c2f60af937f23b7b532600390e8c8b',
|
||||
takerAddress: '0xa2b31dacf30a9c50ca473337c01d8a201ae33e32',
|
||||
makerAssetAmount: '10000000000000000',
|
||||
takerAssetAmount: '20000000000000000',
|
||||
expirationTimeSeconds: '1532560590',
|
||||
makerAssetAmount: new BigNumber('10000000000000000'),
|
||||
takerAssetAmount: new BigNumber('20000000000000000'),
|
||||
expirationTimeSeconds: new BigNumber('1532560590'),
|
||||
makerAssetData: '0xf47261b04c32345ced77393b3530b1eed0f346429d',
|
||||
takerAssetData: '0x0257179264389b814a946f3e92105513705ca6b990',
|
||||
exchangeAddress: '0x12459c951127e0c374ff9105dda097662a027093',
|
||||
};
|
||||
const url = `${relayUrl}/order_config`;
|
||||
it('gets order config', async () => {
|
||||
fetchMock.post(url, orderConfigResponseJSON);
|
||||
fetchMock.get(url, orderConfigResponseJSON);
|
||||
const fees = await relayerClient.getOrderConfigAsync(request);
|
||||
expect(fees).to.be.deep.equal(orderConfigResponse);
|
||||
});
|
||||
it('does not mutate input', async () => {
|
||||
fetchMock.post(url, orderConfigResponseJSON);
|
||||
fetchMock.get(url, orderConfigResponseJSON);
|
||||
const makerAssetAmountBefore = request.makerAssetAmount;
|
||||
const takerAssetAmountBefore = request.takerAssetAmount;
|
||||
const expirationTimeSecondsBefore = request.expirationTimeSeconds;
|
||||
@@ -162,7 +163,7 @@ describe('HttpClient', () => {
|
||||
expect(expirationTimeSecondsBefore).to.be.deep.equal(request.expirationTimeSeconds);
|
||||
});
|
||||
it('throws an error for invalid JSON response', async () => {
|
||||
fetchMock.post(url, { test: 'dummy' });
|
||||
fetchMock.get(url, { test: 'dummy' });
|
||||
expect(relayerClient.getOrderConfigAsync(request)).to.be.rejected();
|
||||
});
|
||||
});
|
||||
|
@@ -1,7 +1,8 @@
|
||||
{
|
||||
"extends": "../../tsconfig",
|
||||
"compilerOptions": {
|
||||
"outDir": "lib"
|
||||
"outDir": "lib",
|
||||
"rootDir": "."
|
||||
},
|
||||
"include": ["./src/**/*", "./test/**/*"]
|
||||
}
|
||||
|
7
packages/connect/typedoc-tsconfig.json
Normal file
7
packages/connect/typedoc-tsconfig.json
Normal file
@@ -0,0 +1,7 @@
|
||||
{
|
||||
"extends": "../../typedoc-tsconfig",
|
||||
"compilerOptions": {
|
||||
"outDir": "lib"
|
||||
},
|
||||
"include": ["./src/**/*", "./test/**/*"]
|
||||
}
|
@@ -1,4 +1,55 @@
|
||||
[
|
||||
{
|
||||
"timestamp": 1537541580,
|
||||
"version": "1.0.4",
|
||||
"changes": [
|
||||
{
|
||||
"note": "Dependencies updated"
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"version": "1.0.3",
|
||||
"changes": [
|
||||
{
|
||||
"note": "Drastically reduce the bundle size by removing unused parts of included contract artifacts."
|
||||
}
|
||||
],
|
||||
"timestamp": 1537369748
|
||||
},
|
||||
{
|
||||
"version": "1.0.2",
|
||||
"changes": [
|
||||
{
|
||||
"note": "Add ZRX & WETH mainnet contract addresses into the included artifacts"
|
||||
}
|
||||
],
|
||||
"timestamp": 1537265493
|
||||
},
|
||||
{
|
||||
"version": "1.0.1",
|
||||
"changes": [
|
||||
{
|
||||
"note": "Add `OrderValidatorWrapper`"
|
||||
},
|
||||
{
|
||||
"note":
|
||||
"Fix bug where contracts not deployed on a network showed an `EXCHANGE_CONTRACT_DOES_NOT_EXIST` error instead of `CONTRACT_NOT_DEPLOYED_ON_NETWORK`",
|
||||
"pr": 1044
|
||||
},
|
||||
{
|
||||
"note":
|
||||
"Export `AssetBalanceAndProxyAllowanceFetcher` and `OrderFilledCancelledFetcher` implementations",
|
||||
"pr": 1054
|
||||
},
|
||||
{
|
||||
"note":
|
||||
"Add `validateOrderFillableOrThrowAsync` and `validateFillOrderThrowIfInvalidAsync` to ExchangeWrapper",
|
||||
"pr": 1054
|
||||
}
|
||||
],
|
||||
"timestamp": 1536142250
|
||||
},
|
||||
{
|
||||
"version": "1.0.1-rc.5",
|
||||
"changes": [
|
||||
|
@@ -5,6 +5,25 @@ Edit the package's CHANGELOG.json file only.
|
||||
|
||||
CHANGELOG
|
||||
|
||||
## v1.0.4 - _September 21, 2018_
|
||||
|
||||
* Dependencies updated
|
||||
|
||||
## v1.0.3 - _September 19, 2018_
|
||||
|
||||
* Drastically reduce the bundle size by removing unused parts of included contract artifacts.
|
||||
|
||||
## v1.0.2 - _September 18, 2018_
|
||||
|
||||
* Add ZRX & WETH mainnet contract addresses into the included artifacts
|
||||
|
||||
## v1.0.1 - _September 5, 2018_
|
||||
|
||||
* Add `OrderValidatorWrapper`
|
||||
* Fix bug where contracts not deployed on a network showed an `EXCHANGE_CONTRACT_DOES_NOT_EXIST` error instead of `CONTRACT_NOT_DEPLOYED_ON_NETWORK` (#1044)
|
||||
* Export `AssetBalanceAndProxyAllowanceFetcher` and `OrderFilledCancelledFetcher` implementations (#1054)
|
||||
* Add `validateOrderFillableOrThrowAsync` and `validateFillOrderThrowIfInvalidAsync` to ExchangeWrapper (#1054)
|
||||
|
||||
## v1.0.1-rc.5 - _August 27, 2018_
|
||||
|
||||
* Fix missing `BlockParamLiteral` type import issue
|
||||
|
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@0xproject/contract-wrappers",
|
||||
"version": "1.0.1-rc.5",
|
||||
"version": "1.0.4",
|
||||
"description": "Smart TS wrappers for 0x smart contracts",
|
||||
"keywords": [
|
||||
"0xproject",
|
||||
@@ -11,26 +11,23 @@
|
||||
"main": "lib/src/index.js",
|
||||
"types": "lib/src/index.d.ts",
|
||||
"scripts": {
|
||||
"watch_without_deps": "yarn pre_build && tsc -w",
|
||||
"build": "yarn pre_build && tsc",
|
||||
"pre_build": "run-s update_artifacts_v2_beta update_artifacts_v2 generate_contract_wrappers copy_artifacts",
|
||||
"generate_contract_wrappers": "abi-gen --abis 'src/artifacts/@(Exchange|DummyERC20Token|DummyERC721Token|ZRXToken|ERC20Token|ERC721Token|WETH9|ERC20Proxy|ERC721Proxy|Forwarder).json' --template ../contract_templates/contract.handlebars --partials '../contract_templates/partials/**/*.handlebars' --output src/contract_wrappers/generated --backend ethers",
|
||||
"build": "yarn pre_build && tsc -b",
|
||||
"pre_build": "run-s update_artifacts generate_contract_wrappers copy_artifacts",
|
||||
"generate_contract_wrappers": "abi-gen --abis 'src/artifacts/@(Exchange|DummyERC20Token|DummyERC721Token|ZRXToken|ERC20Token|ERC721Token|WETH9|ERC20Proxy|ERC721Proxy|Forwarder|OrderValidator).json' --template ../contract_templates/contract.handlebars --partials '../contract_templates/partials/**/*.handlebars' --output src/contract_wrappers/generated --backend ethers",
|
||||
"lint": "tslint --project . --exclude **/src/contract_wrappers/**/* --exclude **/lib/**/*",
|
||||
"test:circleci": "run-s test:coverage",
|
||||
"test": "yarn run_mocha",
|
||||
"rebuild_and_test": "run-s build test",
|
||||
"test:coverage": "nyc npm run test --all && yarn coverage:report:lcov",
|
||||
"coverage:report:lcov": "nyc report --reporter=text-lcov > coverage/lcov.info",
|
||||
"update_artifacts_v2_beta": "for i in ${npm_package_config_contracts_v2_beta}; do copyfiles -u 4 ../migrations/artifacts/2.0.0-beta-testnet/$i.json src/artifacts; done;",
|
||||
"update_artifacts_v2": "for i in ${npm_package_config_contracts_v2}; do copyfiles -u 4 ../migrations/artifacts/2.0.0/$i.json src/artifacts; done;",
|
||||
"update_artifacts": "for i in ${npm_package_config_contracts_v2}; do copyfiles -u 4 ../migrations/artifacts/2.0.0-trimmed/$i.json src/artifacts; done;",
|
||||
"copy_artifacts": "copyfiles -u 2 './src/artifacts/**/*.json' ./lib/src/artifacts",
|
||||
"clean": "shx rm -rf _bundles lib test_temp test/artifacts src/contract_wrappers/generated src/artifacts generated_docs",
|
||||
"run_mocha": "mocha --require source-map-support/register --require make-promises-safe lib/test/**/*_test.js lib/test/global_hooks.js --timeout 10000 --bail --exit",
|
||||
"docs:json": "typedoc --excludePrivate --excludeExternals --target ES5 --json $JSON_FILE_PATH $PROJECT_FILES"
|
||||
"docs:json": "typedoc --excludePrivate --excludeExternals --target ES5 --tsconfig typedoc-tsconfig.json --json $JSON_FILE_PATH $PROJECT_FILES"
|
||||
},
|
||||
"config": {
|
||||
"contracts_v2_beta": "AssetProxyOwner Exchange ERC20Proxy ERC20Token ERC721Proxy ERC721Token WETH9 ZRXToken Forwarder OrderValidator",
|
||||
"contracts_v2": "DummyERC20Token DummyERC721Token",
|
||||
"contracts_v2": "AssetProxyOwner Exchange ERC20Proxy ERC20Token ERC721Proxy ERC721Token WETH9 ZRXToken Forwarder OrderValidator DummyERC20Token DummyERC721Token",
|
||||
"postpublish": {
|
||||
"assets": []
|
||||
}
|
||||
@@ -44,16 +41,17 @@
|
||||
"node": ">=6.0.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@0xproject/abi-gen": "^1.0.7",
|
||||
"@0xproject/dev-utils": "^1.0.6",
|
||||
"@0xproject/migrations": "^1.0.6",
|
||||
"@0xproject/subproviders": "^2.0.1",
|
||||
"@0xproject/tslint-config": "^1.0.6",
|
||||
"@0xproject/abi-gen": "^1.0.9",
|
||||
"@0xproject/dev-utils": "^1.0.8",
|
||||
"@0xproject/migrations": "^1.0.10",
|
||||
"@0xproject/subproviders": "^2.0.3",
|
||||
"@0xproject/tslint-config": "^1.0.7",
|
||||
"@types/lodash": "4.14.104",
|
||||
"@types/mocha": "^2.2.42",
|
||||
"@types/node": "^8.0.53",
|
||||
"@types/node": "*",
|
||||
"@types/sinon": "^2.2.2",
|
||||
"@types/uuid": "^3.4.2",
|
||||
"@types/web3-provider-engine": "^14.0.0",
|
||||
"awesome-typescript-loader": "^3.1.3",
|
||||
"chai": "^4.0.1",
|
||||
"chai-as-promised": "^7.1.0",
|
||||
@@ -74,16 +72,16 @@
|
||||
"web3-provider-engine": "14.0.6"
|
||||
},
|
||||
"dependencies": {
|
||||
"@0xproject/assert": "^1.0.7",
|
||||
"@0xproject/base-contract": "^2.0.1",
|
||||
"@0xproject/fill-scenarios": "^1.0.1-rc.5",
|
||||
"@0xproject/json-schemas": "^1.0.1-rc.6",
|
||||
"@0xproject/order-utils": "^1.0.1-rc.6",
|
||||
"@0xproject/types": "^1.0.1-rc.6",
|
||||
"@0xproject/typescript-typings": "^1.0.5",
|
||||
"@0xproject/utils": "^1.0.7",
|
||||
"@0xproject/web3-wrapper": "^2.0.1",
|
||||
"ethereum-types": "^1.0.5",
|
||||
"@0xproject/assert": "^1.0.9",
|
||||
"@0xproject/base-contract": "^2.0.3",
|
||||
"@0xproject/fill-scenarios": "^1.0.3",
|
||||
"@0xproject/json-schemas": "^1.0.2",
|
||||
"@0xproject/order-utils": "^1.0.3",
|
||||
"@0xproject/types": "^1.0.2",
|
||||
"@0xproject/typescript-typings": "^2.0.1",
|
||||
"@0xproject/utils": "^1.0.9",
|
||||
"@0xproject/web3-wrapper": "^2.0.3",
|
||||
"ethereum-types": "^1.0.7",
|
||||
"ethereumjs-blockstream": "5.0.0",
|
||||
"ethereumjs-util": "^5.1.1",
|
||||
"ethers": "3.0.22",
|
||||
|
@@ -8,6 +8,7 @@ import * as ERC721Proxy from './artifacts/ERC721Proxy.json';
|
||||
import * as ERC721Token from './artifacts/ERC721Token.json';
|
||||
import * as Exchange from './artifacts/Exchange.json';
|
||||
import * as Forwarder from './artifacts/Forwarder.json';
|
||||
import * as OrderValidator from './artifacts/OrderValidator.json';
|
||||
import * as EtherToken from './artifacts/WETH9.json';
|
||||
import * as ZRXToken from './artifacts/ZRXToken.json';
|
||||
|
||||
@@ -22,4 +23,5 @@ export const artifacts = {
|
||||
ERC20Proxy: (ERC20Proxy as any) as ContractArtifact,
|
||||
ERC721Proxy: (ERC721Proxy as any) as ContractArtifact,
|
||||
Forwarder: (Forwarder as any) as ContractArtifact,
|
||||
OrderValidator: (OrderValidator as any) as ContractArtifact,
|
||||
};
|
||||
|
@@ -12,6 +12,7 @@ import { ERC721TokenWrapper } from './contract_wrappers/erc721_token_wrapper';
|
||||
import { EtherTokenWrapper } from './contract_wrappers/ether_token_wrapper';
|
||||
import { ExchangeWrapper } from './contract_wrappers/exchange_wrapper';
|
||||
import { ForwarderWrapper } from './contract_wrappers/forwarder_wrapper';
|
||||
import { OrderValidatorWrapper } from './contract_wrappers/order_validator_wrapper';
|
||||
import { ContractWrappersConfigSchema } from './schemas/contract_wrappers_config_schema';
|
||||
import { contractWrappersPrivateNetworkConfigSchema } from './schemas/contract_wrappers_private_network_config_schema';
|
||||
import { contractWrappersPublicNetworkConfigSchema } from './schemas/contract_wrappers_public_network_config_schema';
|
||||
@@ -52,6 +53,10 @@ export class ContractWrappers {
|
||||
* An instance of the ForwarderWrapper class containing methods for interacting with any Forwarder smart contract.
|
||||
*/
|
||||
public forwarder: ForwarderWrapper;
|
||||
/**
|
||||
* An instance of the OrderValidatorWrapper class containing methods for interacting with any OrderValidator smart contract.
|
||||
*/
|
||||
public orderValidator: OrderValidatorWrapper;
|
||||
|
||||
private _web3Wrapper: Web3Wrapper;
|
||||
/**
|
||||
@@ -106,6 +111,8 @@ export class ContractWrappers {
|
||||
this.exchange = new ExchangeWrapper(
|
||||
this._web3Wrapper,
|
||||
config.networkId,
|
||||
this.erc20Token,
|
||||
this.erc721Token,
|
||||
config.exchangeContractAddress,
|
||||
config.zrxContractAddress,
|
||||
blockPollingIntervalMs,
|
||||
@@ -116,6 +123,7 @@ export class ContractWrappers {
|
||||
config.forwarderContractAddress,
|
||||
config.zrxContractAddress,
|
||||
);
|
||||
this.orderValidator = new OrderValidatorWrapper(this._web3Wrapper, config.networkId);
|
||||
}
|
||||
/**
|
||||
* Sets a new web3 provider for 0x.js. Updating the provider will stop all
|
||||
|
@@ -145,9 +145,12 @@ export abstract class ContractWrapper {
|
||||
}
|
||||
protected _getContractAddress(artifact: ContractArtifact, addressIfExists?: string): string {
|
||||
if (_.isUndefined(addressIfExists)) {
|
||||
if (_.isUndefined(artifact.networks[this._networkId])) {
|
||||
throw new Error(ContractWrappersError.ContractNotDeployedOnNetwork);
|
||||
}
|
||||
const contractAddress = artifact.networks[this._networkId].address;
|
||||
if (_.isUndefined(contractAddress)) {
|
||||
throw new Error(ContractWrappersError.ExchangeContractDoesNotExist);
|
||||
throw new Error(CONTRACT_NAME_TO_NOT_FOUND_ERROR[artifact.contractName]);
|
||||
}
|
||||
return contractAddress;
|
||||
} else {
|
||||
|
@@ -1,12 +1,19 @@
|
||||
import { schemas } from '@0xproject/json-schemas';
|
||||
import { assetDataUtils } from '@0xproject/order-utils';
|
||||
import {
|
||||
assetDataUtils,
|
||||
BalanceAndProxyAllowanceLazyStore,
|
||||
ExchangeTransferSimulator,
|
||||
OrderValidationUtils,
|
||||
} from '@0xproject/order-utils';
|
||||
import { AssetProxyId, Order, SignedOrder } from '@0xproject/types';
|
||||
import { BigNumber } from '@0xproject/utils';
|
||||
import { Web3Wrapper } from '@0xproject/web3-wrapper';
|
||||
import { ContractAbi, LogWithDecodedArgs } from 'ethereum-types';
|
||||
import { BlockParamLiteral, ContractAbi, LogWithDecodedArgs } from 'ethereum-types';
|
||||
import * as _ from 'lodash';
|
||||
|
||||
import { artifacts } from '../artifacts';
|
||||
import { AssetBalanceAndProxyAllowanceFetcher } from '../fetchers/asset_balance_and_proxy_allowance_fetcher';
|
||||
import { OrderFilledCancelledFetcher } from '../fetchers/order_filled_cancelled_fetcher';
|
||||
import { methodOptsSchema } from '../schemas/method_opts_schema';
|
||||
import { orderTxOptsSchema } from '../schemas/order_tx_opts_schema';
|
||||
import { txOptsSchema } from '../schemas/tx_opts_schema';
|
||||
@@ -17,13 +24,17 @@ import {
|
||||
IndexedFilterValues,
|
||||
MethodOpts,
|
||||
OrderInfo,
|
||||
OrderStatus,
|
||||
OrderTransactionOpts,
|
||||
ValidateOrderFillableOpts,
|
||||
} from '../types';
|
||||
import { assert } from '../utils/assert';
|
||||
import { decorators } from '../utils/decorators';
|
||||
import { TransactionEncoder } from '../utils/transaction_encoder';
|
||||
|
||||
import { ContractWrapper } from './contract_wrapper';
|
||||
import { ERC20TokenWrapper } from './erc20_token_wrapper';
|
||||
import { ERC721TokenWrapper } from './erc721_token_wrapper';
|
||||
import { ExchangeContract, ExchangeEventArgs, ExchangeEvents } from './generated/exchange';
|
||||
|
||||
/**
|
||||
@@ -33,6 +44,8 @@ import { ExchangeContract, ExchangeEventArgs, ExchangeEvents } from './generated
|
||||
export class ExchangeWrapper extends ContractWrapper {
|
||||
public abi: ContractAbi = artifacts.Exchange.compilerOutput.abi;
|
||||
private _exchangeContractIfExists?: ExchangeContract;
|
||||
private _erc721TokenWrapper: ERC721TokenWrapper;
|
||||
private _erc20TokenWrapper: ERC20TokenWrapper;
|
||||
private _contractAddressIfExists?: string;
|
||||
private _zrxContractAddressIfExists?: string;
|
||||
/**
|
||||
@@ -48,11 +61,15 @@ export class ExchangeWrapper extends ContractWrapper {
|
||||
constructor(
|
||||
web3Wrapper: Web3Wrapper,
|
||||
networkId: number,
|
||||
erc20TokenWrapper: ERC20TokenWrapper,
|
||||
erc721TokenWrapper: ERC721TokenWrapper,
|
||||
contractAddressIfExists?: string,
|
||||
zrxContractAddressIfExists?: string,
|
||||
blockPollingIntervalMs?: number,
|
||||
) {
|
||||
super(web3Wrapper, networkId, blockPollingIntervalMs);
|
||||
this._erc20TokenWrapper = erc20TokenWrapper;
|
||||
this._erc721TokenWrapper = erc721TokenWrapper;
|
||||
this._contractAddressIfExists = contractAddressIfExists;
|
||||
this._zrxContractAddressIfExists = zrxContractAddressIfExists;
|
||||
}
|
||||
@@ -1084,6 +1101,64 @@ export class ExchangeWrapper extends ContractWrapper {
|
||||
);
|
||||
return logs;
|
||||
}
|
||||
/**
|
||||
* Validate if the supplied order is fillable, and throw if it isn't
|
||||
* @param signedOrder SignedOrder of interest
|
||||
* @param opts ValidateOrderFillableOpts options (e.g expectedFillTakerTokenAmount.
|
||||
* If it isn't supplied, we check if the order is fillable for a non-zero amount)
|
||||
*/
|
||||
public async validateOrderFillableOrThrowAsync(
|
||||
signedOrder: SignedOrder,
|
||||
opts: ValidateOrderFillableOpts = {},
|
||||
): Promise<void> {
|
||||
const balanceAllowanceFetcher = new AssetBalanceAndProxyAllowanceFetcher(
|
||||
this._erc20TokenWrapper,
|
||||
this._erc721TokenWrapper,
|
||||
BlockParamLiteral.Latest,
|
||||
);
|
||||
const balanceAllowanceStore = new BalanceAndProxyAllowanceLazyStore(balanceAllowanceFetcher);
|
||||
const exchangeTradeSimulator = new ExchangeTransferSimulator(balanceAllowanceStore);
|
||||
|
||||
const expectedFillTakerTokenAmountIfExists = opts.expectedFillTakerTokenAmount;
|
||||
const filledCancelledFetcher = new OrderFilledCancelledFetcher(this, BlockParamLiteral.Latest);
|
||||
const orderValidationUtils = new OrderValidationUtils(filledCancelledFetcher);
|
||||
await orderValidationUtils.validateOrderFillableOrThrowAsync(
|
||||
exchangeTradeSimulator,
|
||||
signedOrder,
|
||||
this.getZRXAssetData(),
|
||||
expectedFillTakerTokenAmountIfExists,
|
||||
);
|
||||
}
|
||||
/**
|
||||
* Validate a call to FillOrder and throw if it wouldn't succeed
|
||||
* @param signedOrder SignedOrder of interest
|
||||
* @param fillTakerAssetAmount Amount we'd like to fill the order for
|
||||
* @param takerAddress The taker of the order
|
||||
*/
|
||||
public async validateFillOrderThrowIfInvalidAsync(
|
||||
signedOrder: SignedOrder,
|
||||
fillTakerAssetAmount: BigNumber,
|
||||
takerAddress: string,
|
||||
): Promise<void> {
|
||||
const balanceAllowanceFetcher = new AssetBalanceAndProxyAllowanceFetcher(
|
||||
this._erc20TokenWrapper,
|
||||
this._erc721TokenWrapper,
|
||||
BlockParamLiteral.Latest,
|
||||
);
|
||||
const balanceAllowanceStore = new BalanceAndProxyAllowanceLazyStore(balanceAllowanceFetcher);
|
||||
const exchangeTradeSimulator = new ExchangeTransferSimulator(balanceAllowanceStore);
|
||||
|
||||
const filledCancelledFetcher = new OrderFilledCancelledFetcher(this, BlockParamLiteral.Latest);
|
||||
const orderValidationUtils = new OrderValidationUtils(filledCancelledFetcher);
|
||||
await orderValidationUtils.validateFillOrderThrowIfInvalidAsync(
|
||||
exchangeTradeSimulator,
|
||||
this._web3Wrapper.getProvider(),
|
||||
signedOrder,
|
||||
fillTakerAssetAmount,
|
||||
takerAddress,
|
||||
this.getZRXAssetData(),
|
||||
);
|
||||
}
|
||||
/**
|
||||
* Retrieves the Ethereum address of the Exchange contract deployed on the network
|
||||
* that the user-passed web3 provider is connected to.
|
||||
|
@@ -0,0 +1,187 @@
|
||||
import { schemas } from '@0xproject/json-schemas';
|
||||
import { SignedOrder } from '@0xproject/types';
|
||||
import { BigNumber } from '@0xproject/utils';
|
||||
import { Web3Wrapper } from '@0xproject/web3-wrapper';
|
||||
import { ContractAbi } from 'ethereum-types';
|
||||
import * as _ from 'lodash';
|
||||
|
||||
import { artifacts } from '../artifacts';
|
||||
import { BalanceAndAllowance, OrderAndTraderInfo, TraderInfo } from '../types';
|
||||
import { assert } from '../utils/assert';
|
||||
|
||||
import { ContractWrapper } from './contract_wrapper';
|
||||
import { OrderValidatorContract } from './generated/order_validator';
|
||||
|
||||
/**
|
||||
* This class includes the functionality related to interacting with the OrderValidator contract.
|
||||
*/
|
||||
export class OrderValidatorWrapper extends ContractWrapper {
|
||||
public abi: ContractAbi = artifacts.OrderValidator.compilerOutput.abi;
|
||||
private _orderValidatorContractIfExists?: OrderValidatorContract;
|
||||
/**
|
||||
* Instantiate OrderValidatorWrapper
|
||||
* @param web3Wrapper Web3Wrapper instance to use
|
||||
* @param networkId Desired networkId
|
||||
*/
|
||||
constructor(web3Wrapper: Web3Wrapper, networkId: number) {
|
||||
super(web3Wrapper, networkId);
|
||||
}
|
||||
/**
|
||||
* Get an object conforming to OrderAndTraderInfo containing on-chain information of the provided order and address
|
||||
* @param order An object conforming to SignedOrder
|
||||
* @param takerAddress An ethereum address
|
||||
* @return OrderAndTraderInfo
|
||||
*/
|
||||
public async getOrderAndTraderInfoAsync(order: SignedOrder, takerAddress: string): Promise<OrderAndTraderInfo> {
|
||||
assert.doesConformToSchema('order', order, schemas.signedOrderSchema);
|
||||
assert.isETHAddressHex('takerAddress', takerAddress);
|
||||
const OrderValidatorContractInstance = await this._getOrderValidatorContractAsync();
|
||||
const orderAndTraderInfo = await OrderValidatorContractInstance.getOrderAndTraderInfo.callAsync(
|
||||
order,
|
||||
takerAddress,
|
||||
);
|
||||
const result = {
|
||||
orderInfo: orderAndTraderInfo[0],
|
||||
traderInfo: orderAndTraderInfo[1],
|
||||
};
|
||||
return result;
|
||||
}
|
||||
/**
|
||||
* Get an array of objects conforming to OrderAndTraderInfo containing on-chain information of the provided orders and addresses
|
||||
* @param orders An array of objects conforming to SignedOrder
|
||||
* @param takerAddresses An array of ethereum addresses
|
||||
* @return array of OrderAndTraderInfo
|
||||
*/
|
||||
public async getOrdersAndTradersInfoAsync(
|
||||
orders: SignedOrder[],
|
||||
takerAddresses: string[],
|
||||
): Promise<OrderAndTraderInfo[]> {
|
||||
assert.doesConformToSchema('orders', orders, schemas.signedOrdersSchema);
|
||||
_.forEach(takerAddresses, (takerAddress, index) =>
|
||||
assert.isETHAddressHex(`takerAddresses[${index}]`, takerAddress),
|
||||
);
|
||||
assert.assert(orders.length === takerAddresses.length, 'Expected orders.length to equal takerAddresses.length');
|
||||
const OrderValidatorContractInstance = await this._getOrderValidatorContractAsync();
|
||||
const ordersAndTradersInfo = await OrderValidatorContractInstance.getOrdersAndTradersInfo.callAsync(
|
||||
orders,
|
||||
takerAddresses,
|
||||
);
|
||||
const orderInfos = ordersAndTradersInfo[0];
|
||||
const traderInfos = ordersAndTradersInfo[1];
|
||||
const result = _.map(orderInfos, (orderInfo, index) => {
|
||||
const traderInfo = traderInfos[index];
|
||||
return {
|
||||
orderInfo,
|
||||
traderInfo,
|
||||
};
|
||||
});
|
||||
return result;
|
||||
}
|
||||
/**
|
||||
* Get an object conforming to TraderInfo containing on-chain balance and allowances for maker and taker of order
|
||||
* @param order An object conforming to SignedOrder
|
||||
* @param takerAddress An ethereum address
|
||||
* @return TraderInfo
|
||||
*/
|
||||
public async getTraderInfoAsync(order: SignedOrder, takerAddress: string): Promise<TraderInfo> {
|
||||
assert.doesConformToSchema('order', order, schemas.signedOrderSchema);
|
||||
assert.isETHAddressHex('takerAddress', takerAddress);
|
||||
const OrderValidatorContractInstance = await this._getOrderValidatorContractAsync();
|
||||
const result = await OrderValidatorContractInstance.getTraderInfo.callAsync(order, takerAddress);
|
||||
return result;
|
||||
}
|
||||
/**
|
||||
* Get an array of objects conforming to TraderInfo containing on-chain balance and allowances for maker and taker of order
|
||||
* @param orders An array of objects conforming to SignedOrder
|
||||
* @param takerAddresses An array of ethereum addresses
|
||||
* @return array of TraderInfo
|
||||
*/
|
||||
public async getTradersInfoAsync(orders: SignedOrder[], takerAddresses: string[]): Promise<TraderInfo[]> {
|
||||
assert.doesConformToSchema('orders', orders, schemas.signedOrdersSchema);
|
||||
_.forEach(takerAddresses, (takerAddress, index) =>
|
||||
assert.isETHAddressHex(`takerAddresses[${index}]`, takerAddress),
|
||||
);
|
||||
assert.assert(orders.length === takerAddresses.length, 'Expected orders.length to equal takerAddresses.length');
|
||||
const OrderValidatorContractInstance = await this._getOrderValidatorContractAsync();
|
||||
const result = await OrderValidatorContractInstance.getTradersInfo.callAsync(orders, takerAddresses);
|
||||
return result;
|
||||
}
|
||||
/**
|
||||
* Get an object conforming to BalanceAndAllowance containing on-chain balance and allowance for some address and assetData
|
||||
* @param address An ethereum address
|
||||
* @param assetData An encoded string that can be decoded by a specified proxy contract
|
||||
* @return BalanceAndAllowance
|
||||
*/
|
||||
public async getBalanceAndAllowanceAsync(address: string, assetData: string): Promise<BalanceAndAllowance> {
|
||||
assert.isETHAddressHex('address', address);
|
||||
assert.isHexString('assetData', assetData);
|
||||
const OrderValidatorContractInstance = await this._getOrderValidatorContractAsync();
|
||||
const balanceAndAllowance = await OrderValidatorContractInstance.getBalanceAndAllowance.callAsync(
|
||||
address,
|
||||
assetData,
|
||||
);
|
||||
const result = {
|
||||
balance: balanceAndAllowance[0],
|
||||
allowance: balanceAndAllowance[1],
|
||||
};
|
||||
return result;
|
||||
}
|
||||
/**
|
||||
* Get an array of objects conforming to BalanceAndAllowance containing on-chain balance and allowance for some address and array of assetDatas
|
||||
* @param address An ethereum address
|
||||
* @param assetDatas An array of encoded strings that can be decoded by a specified proxy contract
|
||||
* @return BalanceAndAllowance
|
||||
*/
|
||||
public async getBalancesAndAllowancesAsync(address: string, assetDatas: string[]): Promise<BalanceAndAllowance[]> {
|
||||
assert.isETHAddressHex('address', address);
|
||||
_.forEach(assetDatas, (assetData, index) => assert.isHexString(`assetDatas[${index}]`, assetData));
|
||||
const OrderValidatorContractInstance = await this._getOrderValidatorContractAsync();
|
||||
const balancesAndAllowances = await OrderValidatorContractInstance.getBalancesAndAllowances.callAsync(
|
||||
address,
|
||||
assetDatas,
|
||||
);
|
||||
const balances = balancesAndAllowances[0];
|
||||
const allowances = balancesAndAllowances[1];
|
||||
const result = _.map(balances, (balance, index) => {
|
||||
const allowance = allowances[index];
|
||||
return {
|
||||
balance,
|
||||
allowance,
|
||||
};
|
||||
});
|
||||
return result;
|
||||
}
|
||||
/**
|
||||
* Get owner address of tokenId by calling `token.ownerOf(tokenId)`, but returns a null owner instead of reverting on an unowned token.
|
||||
* @param tokenAddress An ethereum address
|
||||
* @param tokenId An ERC721 tokenId
|
||||
* @return Owner of tokenId or null address if unowned
|
||||
*/
|
||||
public async getERC721TokenOwnerAsync(tokenAddress: string, tokenId: BigNumber): Promise<string | undefined> {
|
||||
assert.isETHAddressHex('tokenAddress', tokenAddress);
|
||||
assert.isBigNumber('tokenId', tokenId);
|
||||
const OrderValidatorContractInstance = await this._getOrderValidatorContractAsync();
|
||||
const result = await OrderValidatorContractInstance.getERC721TokenOwner.callAsync(tokenAddress, tokenId);
|
||||
return result;
|
||||
}
|
||||
// HACK: We don't want this method to be visible to the other units within that package but not to the end user.
|
||||
// TS doesn't give that possibility and therefore we make it private and access it over an any cast. Because of that tslint sees it as unused.
|
||||
// tslint:disable-next-line:no-unused-variable
|
||||
private _invalidateContractInstance(): void {
|
||||
delete this._orderValidatorContractIfExists;
|
||||
}
|
||||
private async _getOrderValidatorContractAsync(): Promise<OrderValidatorContract> {
|
||||
if (!_.isUndefined(this._orderValidatorContractIfExists)) {
|
||||
return this._orderValidatorContractIfExists;
|
||||
}
|
||||
const [abi, address] = await this._getContractAbiAndAddressFromArtifactsAsync(artifacts.OrderValidator);
|
||||
const contractInstance = new OrderValidatorContract(
|
||||
abi,
|
||||
address,
|
||||
this._web3Wrapper.getProvider(),
|
||||
this._web3Wrapper.getContractDefaults(),
|
||||
);
|
||||
this._orderValidatorContractIfExists = contractInstance;
|
||||
return this._orderValidatorContractIfExists;
|
||||
}
|
||||
}
|
@@ -1,8 +1,11 @@
|
||||
// tslint:disable:no-unnecessary-type-assertion
|
||||
import { BlockParamLiteral, ERC20TokenWrapper, ERC721TokenWrapper } from '@0xproject/contract-wrappers';
|
||||
import { AbstractBalanceAndProxyAllowanceFetcher, assetDataUtils } from '@0xproject/order-utils';
|
||||
import { AssetProxyId, ERC20AssetData, ERC721AssetData } from '@0xproject/types';
|
||||
import { BigNumber } from '@0xproject/utils';
|
||||
import { BlockParamLiteral } from 'ethereum-types';
|
||||
|
||||
import { ERC20TokenWrapper } from '../contract_wrappers/erc20_token_wrapper';
|
||||
import { ERC721TokenWrapper } from '../contract_wrappers/erc721_token_wrapper';
|
||||
|
||||
export class AssetBalanceAndProxyAllowanceFetcher implements AbstractBalanceAndProxyAllowanceFetcher {
|
||||
private readonly _erc20Token: ERC20TokenWrapper;
|
@@ -1,7 +1,10 @@
|
||||
// tslint:disable:no-unnecessary-type-assertion
|
||||
import { BlockParamLiteral, ExchangeWrapper } from '@0xproject/contract-wrappers';
|
||||
import { AbstractOrderFilledCancelledFetcher } from '@0xproject/order-utils';
|
||||
import { BigNumber } from '@0xproject/utils';
|
||||
import { BlockParamLiteral } from 'ethereum-types';
|
||||
|
||||
import { ERC20TokenWrapper } from '../contract_wrappers/erc20_token_wrapper';
|
||||
import { ExchangeWrapper } from '../contract_wrappers/exchange_wrapper';
|
||||
|
||||
export class OrderFilledCancelledFetcher implements AbstractOrderFilledCancelledFetcher {
|
||||
private readonly _exchange: ExchangeWrapper;
|
@@ -6,6 +6,7 @@ export { ExchangeWrapper } from './contract_wrappers/exchange_wrapper';
|
||||
export { ERC20ProxyWrapper } from './contract_wrappers/erc20_proxy_wrapper';
|
||||
export { ERC721ProxyWrapper } from './contract_wrappers/erc721_proxy_wrapper';
|
||||
export { ForwarderWrapper } from './contract_wrappers/forwarder_wrapper';
|
||||
export { OrderValidatorWrapper } from './contract_wrappers/order_validator_wrapper';
|
||||
|
||||
export { TransactionEncoder } from './utils/transaction_encoder';
|
||||
|
||||
@@ -21,6 +22,10 @@ export {
|
||||
OrderInfo,
|
||||
EventCallback,
|
||||
DecodedLogEvent,
|
||||
BalanceAndAllowance,
|
||||
OrderAndTraderInfo,
|
||||
TraderInfo,
|
||||
ValidateOrderFillableOpts,
|
||||
} from './types';
|
||||
|
||||
export { Order, SignedOrder, AssetProxyId } from '@0xproject/types';
|
||||
@@ -81,3 +86,8 @@ export {
|
||||
ExchangeEventArgs,
|
||||
ExchangeEvents,
|
||||
} from './contract_wrappers/generated/exchange';
|
||||
|
||||
export { AbstractBalanceAndProxyAllowanceFetcher, AbstractOrderFilledCancelledFetcher } from '@0xproject/order-utils';
|
||||
|
||||
export { AssetBalanceAndProxyAllowanceFetcher } from './fetchers/asset_balance_and_proxy_allowance_fetcher';
|
||||
export { OrderFilledCancelledFetcher } from './fetchers/order_filled_cancelled_fetcher';
|
||||
|
@@ -188,3 +188,24 @@ export enum OrderStatus {
|
||||
FULLY_FILLED,
|
||||
CANCELLED,
|
||||
}
|
||||
|
||||
export interface TraderInfo {
|
||||
makerBalance: BigNumber;
|
||||
makerAllowance: BigNumber;
|
||||
takerBalance: BigNumber;
|
||||
takerAllowance: BigNumber;
|
||||
makerZrxBalance: BigNumber;
|
||||
makerZrxAllowance: BigNumber;
|
||||
takerZrxBalance: BigNumber;
|
||||
takerZrxAllowance: BigNumber;
|
||||
}
|
||||
|
||||
export interface OrderAndTraderInfo {
|
||||
orderInfo: OrderInfo;
|
||||
traderInfo: TraderInfo;
|
||||
}
|
||||
|
||||
export interface BalanceAndAllowance {
|
||||
balance: BigNumber;
|
||||
allowance: BigNumber;
|
||||
}
|
||||
|
@@ -24,7 +24,7 @@ const contractCallErrorTransformer = (error: Error) => {
|
||||
const schemaErrorTransformer = (error: Error) => {
|
||||
if (_.includes(error.message, constants.INVALID_TAKER_FORMAT)) {
|
||||
const errMsg =
|
||||
'Order taker must be of type string. If you want anyone to be able to fill an order - pass ZeroEx.NULL_ADDRESS';
|
||||
'Order taker must be of type string. If you want anyone to be able to fill an order - pass NULL_ADDRESS';
|
||||
return new Error(errMsg);
|
||||
}
|
||||
return error;
|
||||
|
@@ -358,7 +358,7 @@ describe('ExchangeWrapper', () => {
|
||||
describe('#getVersionAsync', () => {
|
||||
it('should return version the hash', async () => {
|
||||
const version = await contractWrappers.exchange.getVersionAsync();
|
||||
const VERSION = '2.0.1-alpha';
|
||||
const VERSION = '2.0.0';
|
||||
expect(version).to.be.equal(VERSION);
|
||||
});
|
||||
});
|
||||
|
@@ -25,10 +25,8 @@ describe('ForwarderWrapper', () => {
|
||||
blockPollingIntervalMs: 0,
|
||||
};
|
||||
const fillableAmount = new BigNumber(5);
|
||||
const takerTokenFillAmount = new BigNumber(5);
|
||||
let contractWrappers: ContractWrappers;
|
||||
let fillScenarios: FillScenarios;
|
||||
let forwarderContractAddress: string;
|
||||
let exchangeContractAddress: string;
|
||||
let zrxTokenAddress: string;
|
||||
let userAddresses: string[];
|
||||
@@ -46,7 +44,6 @@ describe('ForwarderWrapper', () => {
|
||||
before(async () => {
|
||||
await blockchainLifecycle.startAsync();
|
||||
contractWrappers = new ContractWrappers(provider, contractWrappersConfig);
|
||||
forwarderContractAddress = contractWrappers.forwarder.getContractAddress();
|
||||
exchangeContractAddress = contractWrappers.exchange.getContractAddress();
|
||||
userAddresses = await web3Wrapper.getAvailableAddressesAsync();
|
||||
zrxTokenAddress = tokenUtils.getProtocolTokenAddress();
|
||||
|
142
packages/contract-wrappers/test/order_validator_wrapper_test.ts
Normal file
142
packages/contract-wrappers/test/order_validator_wrapper_test.ts
Normal file
@@ -0,0 +1,142 @@
|
||||
import { BlockchainLifecycle, callbackErrorReporter } from '@0xproject/dev-utils';
|
||||
import { FillScenarios } from '@0xproject/fill-scenarios';
|
||||
import { assetDataUtils, orderHashUtils } from '@0xproject/order-utils';
|
||||
import { DoneCallback, SignedOrder } from '@0xproject/types';
|
||||
import { BigNumber } from '@0xproject/utils';
|
||||
import * as chai from 'chai';
|
||||
import { BlockParamLiteral } from 'ethereum-types';
|
||||
import * as _ from 'lodash';
|
||||
import 'mocha';
|
||||
|
||||
import { ContractWrappers, ExchangeCancelEventArgs, ExchangeEvents, ExchangeFillEventArgs, OrderStatus } from '../src';
|
||||
import { DecodedLogEvent, OrderInfo, TraderInfo } from '../src/types';
|
||||
|
||||
import { chaiSetup } from './utils/chai_setup';
|
||||
import { constants } from './utils/constants';
|
||||
import { tokenUtils } from './utils/token_utils';
|
||||
import { provider, web3Wrapper } from './utils/web3_wrapper';
|
||||
|
||||
chaiSetup.configure();
|
||||
const expect = chai.expect;
|
||||
const blockchainLifecycle = new BlockchainLifecycle(web3Wrapper);
|
||||
|
||||
describe('OrderValidator', () => {
|
||||
const contractWrappersConfig = {
|
||||
networkId: constants.TESTRPC_NETWORK_ID,
|
||||
blockPollingIntervalMs: 0,
|
||||
};
|
||||
const fillableAmount = new BigNumber(5);
|
||||
const partialFillAmount = new BigNumber(2);
|
||||
let contractWrappers: ContractWrappers;
|
||||
let fillScenarios: FillScenarios;
|
||||
let exchangeContractAddress: string;
|
||||
let zrxTokenAddress: string;
|
||||
let zrxTokenAssetData: string;
|
||||
let userAddresses: string[];
|
||||
let coinbase: string;
|
||||
let makerAddress: string;
|
||||
let takerAddress: string;
|
||||
let feeRecipient: string;
|
||||
let anotherMakerAddress: string;
|
||||
let makerTokenAddress: string;
|
||||
let takerTokenAddress: string;
|
||||
let makerAssetData: string;
|
||||
let takerAssetData: string;
|
||||
let signedOrder: SignedOrder;
|
||||
let anotherSignedOrder: SignedOrder;
|
||||
before(async () => {
|
||||
await blockchainLifecycle.startAsync();
|
||||
contractWrappers = new ContractWrappers(provider, contractWrappersConfig);
|
||||
exchangeContractAddress = contractWrappers.exchange.getContractAddress();
|
||||
userAddresses = await web3Wrapper.getAvailableAddressesAsync();
|
||||
zrxTokenAddress = tokenUtils.getProtocolTokenAddress();
|
||||
zrxTokenAssetData = assetDataUtils.encodeERC20AssetData(zrxTokenAddress);
|
||||
fillScenarios = new FillScenarios(
|
||||
provider,
|
||||
userAddresses,
|
||||
zrxTokenAddress,
|
||||
exchangeContractAddress,
|
||||
contractWrappers.erc20Proxy.getContractAddress(),
|
||||
contractWrappers.erc721Proxy.getContractAddress(),
|
||||
);
|
||||
[coinbase, makerAddress, takerAddress, feeRecipient, anotherMakerAddress] = userAddresses;
|
||||
[makerTokenAddress] = tokenUtils.getDummyERC20TokenAddresses();
|
||||
takerTokenAddress = tokenUtils.getWethTokenAddress();
|
||||
[makerAssetData, takerAssetData] = [
|
||||
assetDataUtils.encodeERC20AssetData(makerTokenAddress),
|
||||
assetDataUtils.encodeERC20AssetData(takerTokenAddress),
|
||||
];
|
||||
|
||||
signedOrder = await fillScenarios.createFillableSignedOrderAsync(
|
||||
makerAssetData,
|
||||
takerAssetData,
|
||||
makerAddress,
|
||||
constants.NULL_ADDRESS,
|
||||
fillableAmount,
|
||||
);
|
||||
anotherSignedOrder = await fillScenarios.createFillableSignedOrderAsync(
|
||||
zrxTokenAssetData,
|
||||
takerAssetData,
|
||||
makerAddress,
|
||||
constants.NULL_ADDRESS,
|
||||
fillableAmount,
|
||||
);
|
||||
});
|
||||
after(async () => {
|
||||
await blockchainLifecycle.revertAsync();
|
||||
});
|
||||
beforeEach(async () => {
|
||||
await blockchainLifecycle.startAsync();
|
||||
});
|
||||
afterEach(async () => {
|
||||
await blockchainLifecycle.revertAsync();
|
||||
});
|
||||
describe('#getOrdersAndTradersInfoAsync', () => {
|
||||
let signedOrders: SignedOrder[];
|
||||
let takerAddresses: string[];
|
||||
let ordersInfo: OrderInfo[];
|
||||
let tradersInfo: TraderInfo[];
|
||||
beforeEach(async () => {
|
||||
signedOrders = [signedOrder, anotherSignedOrder];
|
||||
takerAddresses = [takerAddress, takerAddress];
|
||||
const ordersAndTradersInfo = await contractWrappers.orderValidator.getOrdersAndTradersInfoAsync(
|
||||
signedOrders,
|
||||
takerAddresses,
|
||||
);
|
||||
ordersInfo = _.map(ordersAndTradersInfo, orderAndTraderInfo => orderAndTraderInfo.orderInfo);
|
||||
tradersInfo = _.map(ordersAndTradersInfo, orderAndTraderInfo => orderAndTraderInfo.traderInfo);
|
||||
});
|
||||
it('should return the same number of order infos and trader infos as input orders', async () => {
|
||||
expect(ordersInfo.length).to.be.equal(signedOrders.length);
|
||||
expect(tradersInfo.length).to.be.equal(takerAddresses.length);
|
||||
});
|
||||
it('should return correct on-chain order info for input orders', async () => {
|
||||
const firstOrderInfo = ordersInfo[0];
|
||||
const secondOrderInfo = ordersInfo[1];
|
||||
expect(firstOrderInfo.orderStatus).to.be.equal(OrderStatus.FILLABLE);
|
||||
expect(firstOrderInfo.orderTakerAssetFilledAmount).to.bignumber.equal(constants.ZERO_AMOUNT);
|
||||
expect(secondOrderInfo.orderStatus).to.be.equal(OrderStatus.FILLABLE);
|
||||
expect(secondOrderInfo.orderTakerAssetFilledAmount).to.bignumber.equal(constants.ZERO_AMOUNT);
|
||||
});
|
||||
it('should return correct on-chain trader info for input takers', async () => {
|
||||
const firstTraderInfo = tradersInfo[0];
|
||||
const secondTraderInfo = tradersInfo[1];
|
||||
expect(firstTraderInfo.makerBalance).to.bignumber.equal(new BigNumber(5));
|
||||
expect(firstTraderInfo.makerAllowance).to.bignumber.equal(new BigNumber(5));
|
||||
expect(firstTraderInfo.takerBalance).to.bignumber.equal(new BigNumber(0));
|
||||
expect(firstTraderInfo.takerAllowance).to.bignumber.equal(new BigNumber(0));
|
||||
expect(firstTraderInfo.makerZrxBalance).to.bignumber.equal(new BigNumber(5));
|
||||
expect(firstTraderInfo.makerZrxAllowance).to.bignumber.equal(new BigNumber(5));
|
||||
expect(firstTraderInfo.takerZrxBalance).to.bignumber.equal(new BigNumber(0));
|
||||
expect(firstTraderInfo.takerZrxAllowance).to.bignumber.equal(new BigNumber(0));
|
||||
expect(secondTraderInfo.makerBalance).to.bignumber.equal(new BigNumber(5));
|
||||
expect(secondTraderInfo.makerAllowance).to.bignumber.equal(new BigNumber(5));
|
||||
expect(secondTraderInfo.takerBalance).to.bignumber.equal(new BigNumber(0));
|
||||
expect(secondTraderInfo.takerAllowance).to.bignumber.equal(new BigNumber(0));
|
||||
expect(secondTraderInfo.makerZrxBalance).to.bignumber.equal(new BigNumber(5));
|
||||
expect(secondTraderInfo.makerZrxAllowance).to.bignumber.equal(new BigNumber(5));
|
||||
expect(secondTraderInfo.takerZrxBalance).to.bignumber.equal(new BigNumber(0));
|
||||
expect(secondTraderInfo.takerZrxAllowance).to.bignumber.equal(new BigNumber(0));
|
||||
});
|
||||
});
|
||||
});
|
@@ -15,4 +15,5 @@ export const constants = {
|
||||
DUMMY_TOKEN_TOTAL_SUPPLY: new BigNumber(10 ** 27), // tslint:disable-line:custom-no-magic-numbers
|
||||
NUM_DUMMY_ERC20_TO_DEPLOY: 3,
|
||||
NUM_DUMMY_ERC721_TO_DEPLOY: 1,
|
||||
ZERO_AMOUNT: new BigNumber(0),
|
||||
};
|
||||
|
@@ -1,7 +1,8 @@
|
||||
{
|
||||
"extends": "../../tsconfig",
|
||||
"compilerOptions": {
|
||||
"outDir": "lib"
|
||||
"outDir": "lib",
|
||||
"rootDir": "."
|
||||
},
|
||||
"include": ["./src/**/*", "./test/**/*"]
|
||||
}
|
||||
|
7
packages/contract-wrappers/typedoc-tsconfig.json
Normal file
7
packages/contract-wrappers/typedoc-tsconfig.json
Normal file
@@ -0,0 +1,7 @@
|
||||
{
|
||||
"extends": "../../typedoc-tsconfig",
|
||||
"compilerOptions": {
|
||||
"outDir": "lib"
|
||||
},
|
||||
"include": ["./src/**/*", "./test/**/*"]
|
||||
}
|
@@ -1,14 +1,35 @@
|
||||
## Contracts
|
||||
|
||||
Smart contracts that implement the 0x protocol.
|
||||
Smart contracts that implement the 0x protocol. Addresses of the deployed contracts can be found [here](https://0xproject.com/wiki#Deployed-Addresses).
|
||||
|
||||
## Usage
|
||||
|
||||
* [Docs](https://0xproject.com/docs/contracts)
|
||||
* [Overview of 0x protocol architecture](https://0xproject.com/wiki#Architecture)
|
||||
* [0x smart contract interactions](https://0xproject.com/wiki#Contract-Interactions)
|
||||
* [Deployed smart contract addresses](https://0xproject.com/wiki#Deployed-Addresses)
|
||||
* [0x protocol message format](https://0xproject.com/wiki#Message-Format)
|
||||
### 2.0.0
|
||||
|
||||
Contracts that make up and interact with version 2.0.0 of the protocol can be found in the `src/2.0.0` directory. The contents of this directory are broken down into the following subdirectories:
|
||||
|
||||
* protocol
|
||||
* This directory contains the contracts that make up version 2.0.0. A full specification can be found [here](https://github.com/0xProject/0x-protocol-specification/blob/master/v2/v2-specification.md).
|
||||
* extensions
|
||||
* This directory contains contracts that interact with the 2.0.0 contracts and will be used in production, such as the [Forwarder](https://github.com/0xProject/0x-protocol-specification/blob/master/v2/forwarder-specification.md) contract.
|
||||
* examples
|
||||
* This directory contains example implementations of contracts that interact with the protocol but are _not_ intended for use in production. Examples include [filter](https://github.com/0xProject/0x-protocol-specification/blob/master/v2/v2-specification.md#filter-contracts) contracts, a [Wallet](https://github.com/0xProject/0x-protocol-specification/blob/master/v2/v2-specification.md#wallet) contract, and a [Validator](https://github.com/0xProject/0x-protocol-specification/blob/master/v2/v2-specification.md#validator) contract, among others.
|
||||
* tokens
|
||||
* This directory contains implementations of different tokens and token standards, including [wETH](https://weth.io/), ZRX, [ERC20](https://github.com/ethereum/EIPs/blob/master/EIPS/eip-20.md), and [ERC721](https://github.com/ethereum/EIPs/blob/master/EIPS/eip-721.md).
|
||||
* multisig
|
||||
* This directory contains the [Gnosis MultiSigWallet](https://github.com/gnosis/MultiSigWallet) and a custom extension that adds a timelock to transactions within the MultiSigWallet.
|
||||
* utils
|
||||
* This directory contains libraries and utils that are shared across all of the other directories.
|
||||
* test
|
||||
* This directory contains mocks and other contracts that are used solely for testing contracts within the other directories.
|
||||
|
||||
### 1.0.0
|
||||
|
||||
Contracts that make up version 1.0.0 of the protocol can be found in `src/1.0.0`. These contracts are considered deprecated and will have limited support going forward.
|
||||
|
||||
## Bug bounty
|
||||
|
||||
A bug bounty for the 2.0.0 contracts is ongoing! Instructions can be found [here](https://0xproject.com/wiki#Bug-Bounty).
|
||||
|
||||
## Contributing
|
||||
|
||||
|
@@ -1,5 +1,5 @@
|
||||
{
|
||||
"artifactsDir": "../migrations/artifacts/2.0.0",
|
||||
"artifactsDir": "../migrations/artifacts/development",
|
||||
"contractsDir": "src/",
|
||||
"compilerSettings": {
|
||||
"optimizer": {
|
||||
@@ -23,6 +23,7 @@
|
||||
"DummyERC20Token",
|
||||
"DummyERC721Receiver",
|
||||
"DummyERC721Token",
|
||||
"DummyMultipleReturnERC20Token",
|
||||
"DummyNoReturnERC20Token",
|
||||
"ERC20Proxy",
|
||||
"ERC20Token",
|
||||
|
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"private": true,
|
||||
"name": "contracts",
|
||||
"version": "2.1.42",
|
||||
"version": "2.1.45",
|
||||
"engines": {
|
||||
"node": ">=6.12"
|
||||
},
|
||||
@@ -11,10 +11,9 @@
|
||||
"test": "test"
|
||||
},
|
||||
"scripts": {
|
||||
"watch_without_deps": "yarn pre_build && tsc -w",
|
||||
"build": "yarn pre_build && tsc",
|
||||
"build": "yarn pre_build && tsc -b",
|
||||
"pre_build": "run-s compile copy_artifacts generate_contract_wrappers",
|
||||
"copy_artifacts": "copyfiles -u 4 '../migrations/artifacts/2.0.0/**/*' ./lib/artifacts;",
|
||||
"copy_artifacts": "copyfiles -u 4 '../migrations/artifacts/development/**/*' ./lib/artifacts;",
|
||||
"test": "yarn run_mocha",
|
||||
"rebuild_and_test": "run-s build test",
|
||||
"test:coverage": "SOLIDITY_COVERAGE=true run-s build run_mocha coverage:report:text coverage:report:lcov",
|
||||
@@ -33,7 +32,7 @@
|
||||
"lint-contracts": "solhint src/2.0.0/**/**/**/**/*.sol"
|
||||
},
|
||||
"config": {
|
||||
"abis": "../migrations/artifacts/2.0.0/@(AssetProxyOwner|DummyERC20Token|DummyERC721Receiver|DummyERC721Token|DummyNoReturnERC20Token|ERC20Proxy|ERC721Proxy|Forwarder|Exchange|ExchangeWrapper|IAssetData|IAssetProxy|InvalidERC721Receiver|MixinAuthorizable|MultiSigWallet|MultiSigWalletWithTimeLock|OrderValidator|ReentrantERC20Token|TestAssetProxyOwner|TestAssetProxyDispatcher|TestConstants|TestExchangeInternals|TestLibBytes|TestLibs|TestSignatureValidator|TestStaticCallReceiver|Validator|Wallet|TokenRegistry|Whitelist|WETH9|ZRXToken).json"
|
||||
"abis": "../migrations/artifacts/development/@(AssetProxyOwner|DummyERC20Token|DummyERC721Receiver|DummyERC721Token|DummyMultipleReturnERC20Token|DummyNoReturnERC20Token|ERC20Proxy|ERC721Proxy|Forwarder|Exchange|ExchangeWrapper|IAssetData|IAssetProxy|InvalidERC721Receiver|MixinAuthorizable|MultiSigWallet|MultiSigWalletWithTimeLock|OrderValidator|ReentrantERC20Token|TestAssetProxyOwner|TestAssetProxyDispatcher|TestConstants|TestExchangeInternals|TestLibBytes|TestLibs|TestSignatureValidator|TestStaticCallReceiver|Validator|Wallet|TokenRegistry|Whitelist|WETH9|ZRXToken).json"
|
||||
},
|
||||
"repository": {
|
||||
"type": "git",
|
||||
@@ -46,16 +45,16 @@
|
||||
},
|
||||
"homepage": "https://github.com/0xProject/0x-monorepo/packages/contracts/README.md",
|
||||
"devDependencies": {
|
||||
"@0xproject/abi-gen": "^1.0.7",
|
||||
"@0xproject/dev-utils": "^1.0.6",
|
||||
"@0xproject/sol-compiler": "^1.1.1",
|
||||
"@0xproject/sol-cov": "^2.1.1",
|
||||
"@0xproject/subproviders": "^2.0.1",
|
||||
"@0xproject/tslint-config": "^1.0.6",
|
||||
"@0xproject/abi-gen": "^1.0.9",
|
||||
"@0xproject/dev-utils": "^1.0.8",
|
||||
"@0xproject/sol-compiler": "^1.1.3",
|
||||
"@0xproject/sol-cov": "^2.1.3",
|
||||
"@0xproject/subproviders": "^2.0.3",
|
||||
"@0xproject/tslint-config": "^1.0.7",
|
||||
"@types/bn.js": "^4.11.0",
|
||||
"@types/ethereumjs-abi": "^0.6.0",
|
||||
"@types/lodash": "4.14.104",
|
||||
"@types/node": "^8.0.53",
|
||||
"@types/node": "*",
|
||||
"@types/yargs": "^10.0.0",
|
||||
"chai": "^4.0.1",
|
||||
"chai-as-promised": "^7.1.0",
|
||||
@@ -73,15 +72,15 @@
|
||||
"yargs": "^10.0.3"
|
||||
},
|
||||
"dependencies": {
|
||||
"@0xproject/base-contract": "^2.0.1",
|
||||
"@0xproject/order-utils": "^1.0.1-rc.6",
|
||||
"@0xproject/types": "^1.0.1-rc.6",
|
||||
"@0xproject/typescript-typings": "^1.0.5",
|
||||
"@0xproject/utils": "^1.0.7",
|
||||
"@0xproject/web3-wrapper": "^2.0.1",
|
||||
"@0xproject/base-contract": "^2.0.3",
|
||||
"@0xproject/order-utils": "^1.0.3",
|
||||
"@0xproject/types": "^1.0.2",
|
||||
"@0xproject/typescript-typings": "^2.0.1",
|
||||
"@0xproject/utils": "^1.0.9",
|
||||
"@0xproject/web3-wrapper": "^2.0.3",
|
||||
"@types/js-combinatorics": "^0.5.29",
|
||||
"bn.js": "^4.11.8",
|
||||
"ethereum-types": "^1.0.5",
|
||||
"ethereum-types": "^1.0.7",
|
||||
"ethereumjs-abi": "0.6.5",
|
||||
"ethereumjs-util": "^5.1.1",
|
||||
"ethers": "3.0.22",
|
||||
|
@@ -34,7 +34,6 @@ contract Forwarder is
|
||||
MixinExchangeWrapper,
|
||||
MixinForwarderCore
|
||||
{
|
||||
|
||||
constructor (
|
||||
address _exchange,
|
||||
bytes memory _zrxAssetData,
|
||||
|
@@ -31,7 +31,6 @@ contract MixinAssets is
|
||||
LibConstants,
|
||||
MAssets
|
||||
{
|
||||
|
||||
using LibBytes for bytes;
|
||||
|
||||
bytes4 constant internal ERC20_TRANSFER_SELECTOR = bytes4(keccak256("transfer(address,uint256)"));
|
||||
|
@@ -34,7 +34,6 @@ contract MixinExchangeWrapper is
|
||||
LibConstants,
|
||||
MExchangeWrapper
|
||||
{
|
||||
|
||||
/// @dev Fills the input order.
|
||||
/// Returns false if the transaction would otherwise revert.
|
||||
/// @param order Order struct containing order specifications.
|
||||
@@ -61,7 +60,7 @@ contract MixinExchangeWrapper is
|
||||
// Call `fillOrder` and handle any exceptions gracefully
|
||||
assembly {
|
||||
let success := call(
|
||||
gas, // forward all gas, TODO: look into gas consumption of assert/throw
|
||||
gas, // forward all gas
|
||||
exchange, // call address of Exchange contract
|
||||
0, // transfer 0 wei
|
||||
add(fillOrderCalldata, 32), // pointer to start of input (skip array length in first 32 bytes)
|
||||
@@ -69,20 +68,14 @@ contract MixinExchangeWrapper is
|
||||
fillOrderCalldata, // write output over input
|
||||
128 // output size is 128 bytes
|
||||
)
|
||||
switch success
|
||||
case 0 {
|
||||
mstore(fillResults, 0)
|
||||
mstore(add(fillResults, 32), 0)
|
||||
mstore(add(fillResults, 64), 0)
|
||||
mstore(add(fillResults, 96), 0)
|
||||
}
|
||||
case 1 {
|
||||
if success {
|
||||
mstore(fillResults, mload(fillOrderCalldata))
|
||||
mstore(add(fillResults, 32), mload(add(fillOrderCalldata, 32)))
|
||||
mstore(add(fillResults, 64), mload(add(fillOrderCalldata, 64)))
|
||||
mstore(add(fillResults, 96), mload(add(fillOrderCalldata, 96)))
|
||||
}
|
||||
}
|
||||
// fillResults values will be 0 by default if call was unsuccessful
|
||||
return fillResults;
|
||||
}
|
||||
|
||||
|
@@ -39,7 +39,6 @@ contract MixinForwarderCore is
|
||||
MExchangeWrapper,
|
||||
IForwarderCore
|
||||
{
|
||||
|
||||
using LibBytes for bytes;
|
||||
|
||||
/// @dev Constructor approves ERC20 proxy to transfer ZRX and WETH on this contract's behalf.
|
||||
@@ -47,10 +46,12 @@ contract MixinForwarderCore is
|
||||
public
|
||||
{
|
||||
address proxyAddress = EXCHANGE.getAssetProxy(ERC20_DATA_ID);
|
||||
if (proxyAddress != address(0)) {
|
||||
ETHER_TOKEN.approve(proxyAddress, MAX_UINT);
|
||||
ZRX_TOKEN.approve(proxyAddress, MAX_UINT);
|
||||
}
|
||||
require(
|
||||
proxyAddress != address(0),
|
||||
"UNREGISTERED_ASSET_PROXY"
|
||||
);
|
||||
ETHER_TOKEN.approve(proxyAddress, MAX_UINT);
|
||||
ZRX_TOKEN.approve(proxyAddress, MAX_UINT);
|
||||
}
|
||||
|
||||
/// @dev Purchases as much of orders' makerAssets as possible by selling up to 95% of transaction's ETH value.
|
||||
|
@@ -28,7 +28,6 @@ contract MixinWeth is
|
||||
LibConstants,
|
||||
MWeth
|
||||
{
|
||||
|
||||
/// @dev Default payabale function, this allows us to withdraw WETH
|
||||
function ()
|
||||
public
|
||||
|
@@ -24,7 +24,6 @@ import "../interfaces/IAssets.sol";
|
||||
contract MAssets is
|
||||
IAssets
|
||||
{
|
||||
|
||||
/// @dev Transfers given amount of asset to sender.
|
||||
/// @param assetData Byte array encoded for the respective asset proxy.
|
||||
/// @param amount Amount of asset to transfer to sender.
|
||||
|
@@ -28,11 +28,11 @@ import "../../utils/LibBytes/LibBytes.sol";
|
||||
|
||||
contract OrderValidator {
|
||||
|
||||
using LibBytes for bytes;
|
||||
|
||||
bytes4 constant internal ERC20_DATA_ID = bytes4(keccak256("ERC20Token(address)"));
|
||||
bytes4 constant internal ERC721_DATA_ID = bytes4(keccak256("ERC721Token(address,uint256)"));
|
||||
|
||||
using LibBytes for bytes;
|
||||
|
||||
struct TraderInfo {
|
||||
uint256 makerBalance; // Maker's balance of makerAsset
|
||||
uint256 makerAllowance; // Maker's allowance to corresponding AssetProxy
|
||||
|
@@ -1,13 +1,14 @@
|
||||
// solhint-disable
|
||||
pragma solidity ^0.4.10;
|
||||
pragma solidity ^0.4.15;
|
||||
|
||||
|
||||
/// @title Multisignature wallet - Allows multiple parties to agree on transactions before execution.
|
||||
/// @author Stefan George - <stefan.george@consensys.net>
|
||||
contract MultiSigWallet {
|
||||
|
||||
uint constant public MAX_OWNER_COUNT = 50;
|
||||
|
||||
/*
|
||||
* Events
|
||||
*/
|
||||
event Confirmation(address indexed sender, uint indexed transactionId);
|
||||
event Revocation(address indexed sender, uint indexed transactionId);
|
||||
event Submission(uint indexed transactionId);
|
||||
@@ -18,6 +19,14 @@ contract MultiSigWallet {
|
||||
event OwnerRemoval(address indexed owner);
|
||||
event RequirementChange(uint required);
|
||||
|
||||
/*
|
||||
* Constants
|
||||
*/
|
||||
uint constant public MAX_OWNER_COUNT = 50;
|
||||
|
||||
/*
|
||||
* Storage
|
||||
*/
|
||||
mapping (uint => Transaction) public transactions;
|
||||
mapping (uint => mapping (address => bool)) public confirmations;
|
||||
mapping (address => bool) public isOwner;
|
||||
@@ -32,60 +41,54 @@ contract MultiSigWallet {
|
||||
bool executed;
|
||||
}
|
||||
|
||||
/*
|
||||
* Modifiers
|
||||
*/
|
||||
modifier onlyWallet() {
|
||||
if (msg.sender != address(this))
|
||||
throw;
|
||||
require(msg.sender == address(this));
|
||||
_;
|
||||
}
|
||||
|
||||
modifier ownerDoesNotExist(address owner) {
|
||||
if (isOwner[owner])
|
||||
throw;
|
||||
require(!isOwner[owner]);
|
||||
_;
|
||||
}
|
||||
|
||||
modifier ownerExists(address owner) {
|
||||
if (!isOwner[owner])
|
||||
throw;
|
||||
require(isOwner[owner]);
|
||||
_;
|
||||
}
|
||||
|
||||
modifier transactionExists(uint transactionId) {
|
||||
if (transactions[transactionId].destination == 0)
|
||||
throw;
|
||||
require(transactions[transactionId].destination != 0);
|
||||
_;
|
||||
}
|
||||
|
||||
modifier confirmed(uint transactionId, address owner) {
|
||||
if (!confirmations[transactionId][owner])
|
||||
throw;
|
||||
require(confirmations[transactionId][owner]);
|
||||
_;
|
||||
}
|
||||
|
||||
modifier notConfirmed(uint transactionId, address owner) {
|
||||
if (confirmations[transactionId][owner])
|
||||
throw;
|
||||
require(!confirmations[transactionId][owner]);
|
||||
_;
|
||||
}
|
||||
|
||||
modifier notExecuted(uint transactionId) {
|
||||
if (transactions[transactionId].executed)
|
||||
throw;
|
||||
require(!transactions[transactionId].executed);
|
||||
_;
|
||||
}
|
||||
|
||||
modifier notNull(address _address) {
|
||||
if (_address == 0)
|
||||
throw;
|
||||
require(_address != 0);
|
||||
_;
|
||||
}
|
||||
|
||||
modifier validRequirement(uint ownerCount, uint _required) {
|
||||
if ( ownerCount > MAX_OWNER_COUNT
|
||||
|| _required > ownerCount
|
||||
|| _required == 0
|
||||
|| ownerCount == 0)
|
||||
throw;
|
||||
require(ownerCount <= MAX_OWNER_COUNT
|
||||
&& _required <= ownerCount
|
||||
&& _required != 0
|
||||
&& ownerCount != 0);
|
||||
_;
|
||||
}
|
||||
|
||||
@@ -108,8 +111,7 @@ contract MultiSigWallet {
|
||||
validRequirement(_owners.length, _required)
|
||||
{
|
||||
for (uint i=0; i<_owners.length; i++) {
|
||||
if (isOwner[_owners[i]] || _owners[i] == 0)
|
||||
throw;
|
||||
require(!isOwner[_owners[i]] && _owners[i] != 0);
|
||||
isOwner[_owners[i]] = true;
|
||||
}
|
||||
owners = _owners;
|
||||
@@ -151,7 +153,7 @@ contract MultiSigWallet {
|
||||
|
||||
/// @dev Allows to replace an owner with a new owner. Transaction has to be sent by wallet.
|
||||
/// @param owner Address of owner to be replaced.
|
||||
/// @param owner Address of new owner.
|
||||
/// @param newOwner Address of new owner.
|
||||
function replaceOwner(address owner, address newOwner)
|
||||
public
|
||||
onlyWallet
|
||||
@@ -222,20 +224,44 @@ contract MultiSigWallet {
|
||||
/// @param transactionId Transaction ID.
|
||||
function executeTransaction(uint transactionId)
|
||||
public
|
||||
ownerExists(msg.sender)
|
||||
confirmed(transactionId, msg.sender)
|
||||
notExecuted(transactionId)
|
||||
{
|
||||
if (isConfirmed(transactionId)) {
|
||||
Transaction tx = transactions[transactionId];
|
||||
tx.executed = true;
|
||||
if (tx.destination.call.value(tx.value)(tx.data))
|
||||
Transaction storage txn = transactions[transactionId];
|
||||
txn.executed = true;
|
||||
if (external_call(txn.destination, txn.value, txn.data.length, txn.data))
|
||||
Execution(transactionId);
|
||||
else {
|
||||
ExecutionFailure(transactionId);
|
||||
tx.executed = false;
|
||||
txn.executed = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// call has been separated into its own function in order to take advantage
|
||||
// of the Solidity's code generator to produce a loop that copies tx.data into memory.
|
||||
function external_call(address destination, uint value, uint dataLength, bytes data) internal returns (bool) {
|
||||
bool result;
|
||||
assembly {
|
||||
let x := mload(0x40) // "Allocate" memory for output (0x40 is where "free memory" pointer is stored by convention)
|
||||
let d := add(data, 32) // First 32 bytes are the padded length of data, so exclude that
|
||||
result := call(
|
||||
sub(gas, 34710), // 34710 is the value that solidity is currently emitting
|
||||
// It includes callGas (700) + callVeryLow (3, to pay for SUB) + callValueTransferGas (9000) +
|
||||
// callNewAccountGas (25000, in case the destination address does not exist and needs creating)
|
||||
destination,
|
||||
value,
|
||||
d,
|
||||
dataLength, // Size of the input (in bytes) - this is what fixes the padding problem
|
||||
x,
|
||||
0 // Output is ignored, therefore the output size is zero
|
||||
)
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
/// @dev Returns the confirmation status of a transaction.
|
||||
/// @param transactionId Transaction ID.
|
||||
/// @return Confirmation status.
|
||||
@@ -364,4 +390,4 @@ contract MultiSigWallet {
|
||||
for (i=from; i<to; i++)
|
||||
_transactionIds[i - from] = transactionIdsTemp[i];
|
||||
}
|
||||
}
|
||||
}
|
@@ -16,47 +16,57 @@
|
||||
|
||||
*/
|
||||
|
||||
// solhint-disable
|
||||
pragma solidity ^0.4.10;
|
||||
pragma solidity 0.4.24;
|
||||
|
||||
import "./MultiSigWallet.sol";
|
||||
|
||||
|
||||
/// @title Multisignature wallet with time lock- Allows multiple parties to execute a transaction after a time lock has passed.
|
||||
/// @author Amir Bandeali - <amir@0xProject.com>
|
||||
contract MultiSigWalletWithTimeLock is MultiSigWallet {
|
||||
// solhint-disable not-rely-on-time
|
||||
contract MultiSigWalletWithTimeLock is
|
||||
MultiSigWallet
|
||||
{
|
||||
event ConfirmationTimeSet(uint256 indexed transactionId, uint256 confirmationTime);
|
||||
event TimeLockChange(uint256 secondsTimeLocked);
|
||||
|
||||
event ConfirmationTimeSet(uint indexed transactionId, uint confirmationTime);
|
||||
event TimeLockChange(uint secondsTimeLocked);
|
||||
uint256 public secondsTimeLocked;
|
||||
|
||||
uint public secondsTimeLocked;
|
||||
mapping (uint256 => uint256) public confirmationTimes;
|
||||
|
||||
mapping (uint => uint) public confirmationTimes;
|
||||
|
||||
modifier notFullyConfirmed(uint transactionId) {
|
||||
require(!isConfirmed(transactionId));
|
||||
modifier notFullyConfirmed(uint256 transactionId) {
|
||||
require(
|
||||
!isConfirmed(transactionId),
|
||||
"TX_FULLY_CONFIRMED"
|
||||
);
|
||||
_;
|
||||
}
|
||||
|
||||
modifier fullyConfirmed(uint transactionId) {
|
||||
require(isConfirmed(transactionId));
|
||||
modifier fullyConfirmed(uint256 transactionId) {
|
||||
require(
|
||||
isConfirmed(transactionId),
|
||||
"TX_NOT_FULLY_CONFIRMED"
|
||||
);
|
||||
_;
|
||||
}
|
||||
|
||||
modifier pastTimeLock(uint transactionId) {
|
||||
require(block.timestamp >= confirmationTimes[transactionId] + secondsTimeLocked);
|
||||
modifier pastTimeLock(uint256 transactionId) {
|
||||
require(
|
||||
block.timestamp >= confirmationTimes[transactionId] + secondsTimeLocked,
|
||||
"TIME_LOCK_INCOMPLETE"
|
||||
);
|
||||
_;
|
||||
}
|
||||
|
||||
/*
|
||||
* Public functions
|
||||
*/
|
||||
|
||||
/// @dev Contract constructor sets initial owners, required number of confirmations, and time lock.
|
||||
/// @param _owners List of initial owners.
|
||||
/// @param _required Number of required confirmations.
|
||||
/// @param _secondsTimeLocked Duration needed after a transaction is confirmed and before it becomes executable, in seconds.
|
||||
function MultiSigWalletWithTimeLock(address[] _owners, uint _required, uint _secondsTimeLocked)
|
||||
constructor (
|
||||
address[] _owners,
|
||||
uint256 _required,
|
||||
uint256 _secondsTimeLocked
|
||||
)
|
||||
public
|
||||
MultiSigWallet(_owners, _required)
|
||||
{
|
||||
@@ -65,17 +75,17 @@ contract MultiSigWalletWithTimeLock is MultiSigWallet {
|
||||
|
||||
/// @dev Changes the duration of the time lock for transactions.
|
||||
/// @param _secondsTimeLocked Duration needed after a transaction is confirmed and before it becomes executable, in seconds.
|
||||
function changeTimeLock(uint _secondsTimeLocked)
|
||||
function changeTimeLock(uint256 _secondsTimeLocked)
|
||||
public
|
||||
onlyWallet
|
||||
{
|
||||
secondsTimeLocked = _secondsTimeLocked;
|
||||
TimeLockChange(_secondsTimeLocked);
|
||||
emit TimeLockChange(_secondsTimeLocked);
|
||||
}
|
||||
|
||||
/// @dev Allows an owner to confirm a transaction.
|
||||
/// @param transactionId Transaction ID.
|
||||
function confirmTransaction(uint transactionId)
|
||||
function confirmTransaction(uint256 transactionId)
|
||||
public
|
||||
ownerExists(msg.sender)
|
||||
transactionExists(transactionId)
|
||||
@@ -83,52 +93,35 @@ contract MultiSigWalletWithTimeLock is MultiSigWallet {
|
||||
notFullyConfirmed(transactionId)
|
||||
{
|
||||
confirmations[transactionId][msg.sender] = true;
|
||||
Confirmation(msg.sender, transactionId);
|
||||
emit Confirmation(msg.sender, transactionId);
|
||||
if (isConfirmed(transactionId)) {
|
||||
setConfirmationTime(transactionId, block.timestamp);
|
||||
}
|
||||
}
|
||||
|
||||
/// @dev Allows an owner to revoke a confirmation for a transaction.
|
||||
/// @param transactionId Transaction ID.
|
||||
function revokeConfirmation(uint transactionId)
|
||||
public
|
||||
ownerExists(msg.sender)
|
||||
confirmed(transactionId, msg.sender)
|
||||
notExecuted(transactionId)
|
||||
notFullyConfirmed(transactionId)
|
||||
{
|
||||
confirmations[transactionId][msg.sender] = false;
|
||||
Revocation(msg.sender, transactionId);
|
||||
}
|
||||
|
||||
/// @dev Allows anyone to execute a confirmed transaction.
|
||||
/// @param transactionId Transaction ID.
|
||||
function executeTransaction(uint transactionId)
|
||||
function executeTransaction(uint256 transactionId)
|
||||
public
|
||||
notExecuted(transactionId)
|
||||
fullyConfirmed(transactionId)
|
||||
pastTimeLock(transactionId)
|
||||
{
|
||||
Transaction storage tx = transactions[transactionId];
|
||||
tx.executed = true;
|
||||
if (tx.destination.call.value(tx.value)(tx.data))
|
||||
Execution(transactionId);
|
||||
else {
|
||||
ExecutionFailure(transactionId);
|
||||
tx.executed = false;
|
||||
Transaction storage txn = transactions[transactionId];
|
||||
txn.executed = true;
|
||||
if (external_call(txn.destination, txn.value, txn.data.length, txn.data)) {
|
||||
emit Execution(transactionId);
|
||||
} else {
|
||||
emit ExecutionFailure(transactionId);
|
||||
txn.executed = false;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Internal functions
|
||||
*/
|
||||
|
||||
/// @dev Sets the time of when a submission first passed.
|
||||
function setConfirmationTime(uint transactionId, uint confirmationTime)
|
||||
function setConfirmationTime(uint256 transactionId, uint256 confirmationTime)
|
||||
internal
|
||||
{
|
||||
confirmationTimes[transactionId] = confirmationTime;
|
||||
ConfirmationTimeSet(transactionId, confirmationTime);
|
||||
emit ConfirmationTimeSet(transactionId, confirmationTime);
|
||||
}
|
||||
}
|
||||
|
@@ -18,7 +18,6 @@
|
||||
|
||||
pragma solidity 0.4.24;
|
||||
|
||||
import "../../utils/LibBytes/LibBytes.sol";
|
||||
import "./MixinAuthorizable.sol";
|
||||
|
||||
|
||||
@@ -59,15 +58,64 @@ contract ERC20Proxy is
|
||||
mstore(96, 0)
|
||||
revert(0, 100)
|
||||
}
|
||||
|
||||
/////// Token contract address ///////
|
||||
// The token address is found as follows:
|
||||
// * It is stored at offset 4 in `assetData` contents.
|
||||
// * This is stored at offset 32 from `assetData`.
|
||||
// * The offset to `assetData` from Params is stored at offset
|
||||
// 4 in calldata.
|
||||
// * The offset of Params in calldata is 4.
|
||||
// So we read location 4 and add 32 + 4 + 4 to it.
|
||||
|
||||
// `transferFrom`.
|
||||
// The function is marked `external`, so no abi decodeding is done for
|
||||
// us. Instead, we expect the `calldata` memory to contain the
|
||||
// following:
|
||||
//
|
||||
// | Area | Offset | Length | Contents |
|
||||
// |----------|--------|---------|-------------------------------------|
|
||||
// | Header | 0 | 4 | function selector |
|
||||
// | Params | | 4 * 32 | function parameters: |
|
||||
// | | 4 | | 1. offset to assetData (*) |
|
||||
// | | 36 | | 2. from |
|
||||
// | | 68 | | 3. to |
|
||||
// | | 100 | | 4. amount |
|
||||
// | Data | | | assetData: |
|
||||
// | | 132 | 32 | assetData Length |
|
||||
// | | 164 | ** | assetData Contents |
|
||||
//
|
||||
// (*): offset is computed from start of function parameters, so offset
|
||||
// by an additional 4 bytes in the calldata.
|
||||
//
|
||||
// (**): see table below to compute length of assetData Contents
|
||||
//
|
||||
// WARNING: The ABIv2 specification allows additional padding between
|
||||
// the Params and Data section. This will result in a larger
|
||||
// offset to assetData.
|
||||
|
||||
// Asset data itself is encoded as follows:
|
||||
//
|
||||
// | Area | Offset | Length | Contents |
|
||||
// |----------|--------|---------|-------------------------------------|
|
||||
// | Header | 0 | 4 | function selector |
|
||||
// | Params | | 1 * 32 | function parameters: |
|
||||
// | | 4 | 12 + 20 | 1. token address |
|
||||
|
||||
// We construct calldata for the `token.transferFrom` ABI.
|
||||
// The layout of this calldata is in the table below.
|
||||
//
|
||||
// | Area | Offset | Length | Contents |
|
||||
// |----------|--------|---------|-------------------------------------|
|
||||
// | Header | 0 | 4 | function selector |
|
||||
// | Params | | 3 * 32 | function parameters: |
|
||||
// | | 4 | | 1. from |
|
||||
// | | 36 | | 2. to |
|
||||
// | | 68 | | 3. amount |
|
||||
|
||||
/////// Read token address from calldata ///////
|
||||
// * The token address is stored in `assetData`.
|
||||
//
|
||||
// * The "offset to assetData" is stored at offset 4 in the calldata (table 1).
|
||||
// [assetDataOffsetFromParams = calldataload(4)]
|
||||
//
|
||||
// * Notes that the "offset to assetData" is relative to the "Params" area of calldata;
|
||||
// add 4 bytes to account for the length of the "Header" area (table 1).
|
||||
// [assetDataOffsetFromHeader = assetDataOffsetFromParams + 4]
|
||||
//
|
||||
// * The "token address" is offset 32+4=36 bytes into "assetData" (tables 1 & 2).
|
||||
// [tokenOffset = assetDataOffsetFromHeader + 36 = calldataload(4) + 4 + 36]
|
||||
let token := calldataload(add(calldataload(4), 40))
|
||||
|
||||
/////// Setup Header Area ///////
|
||||
|
@@ -18,7 +18,6 @@
|
||||
|
||||
pragma solidity 0.4.24;
|
||||
|
||||
import "../../utils/LibBytes/LibBytes.sol";
|
||||
import "./MixinAuthorizable.sol";
|
||||
|
||||
|
||||
@@ -80,6 +79,8 @@ contract ERC721Proxy is
|
||||
// (*): offset is computed from start of function parameters, so offset
|
||||
// by an additional 4 bytes in the calldata.
|
||||
//
|
||||
// (**): see table below to compute length of assetData Contents
|
||||
//
|
||||
// WARNING: The ABIv2 specification allows additional padding between
|
||||
// the Params and Data section. This will result in a larger
|
||||
// offset to assetData.
|
||||
|
@@ -26,7 +26,6 @@ contract MixinAuthorizable is
|
||||
Ownable,
|
||||
MAuthorizable
|
||||
{
|
||||
|
||||
/// @dev Only authorized addresses can invoke functions with this modifier.
|
||||
modifier onlyAuthorized {
|
||||
require(
|
||||
|
@@ -24,7 +24,6 @@ import "./IAuthorizable.sol";
|
||||
contract IAssetProxy is
|
||||
IAuthorizable
|
||||
{
|
||||
|
||||
/// @dev Transfers assets. Either succeeds or throws.
|
||||
/// @param assetData Byte array encoded for the respective asset proxy.
|
||||
/// @param from Address to transfer asset from.
|
||||
|
@@ -24,7 +24,6 @@ import "../../../utils/Ownable/IOwnable.sol";
|
||||
contract IAuthorizable is
|
||||
IOwnable
|
||||
{
|
||||
|
||||
/// @dev Authorizes an address.
|
||||
/// @param target Address to authorize.
|
||||
function addAuthorizedAddress(address target)
|
||||
|
@@ -24,7 +24,6 @@ import "../interfaces/IAuthorizable.sol";
|
||||
contract MAuthorizable is
|
||||
IAuthorizable
|
||||
{
|
||||
|
||||
// Event logged when a new address is authorized.
|
||||
event AuthorizedAddressAdded(
|
||||
address indexed target,
|
||||
|
@@ -16,14 +16,16 @@
|
||||
|
||||
*/
|
||||
|
||||
pragma solidity 0.4.10;
|
||||
pragma solidity 0.4.24;
|
||||
|
||||
import "../../multisig/MultiSigWalletWithTimeLock.sol";
|
||||
import "../../utils/LibBytes/LibBytes.sol";
|
||||
|
||||
|
||||
contract AssetProxyOwner is
|
||||
MultiSigWalletWithTimeLock
|
||||
{
|
||||
using LibBytes for bytes;
|
||||
|
||||
event AssetProxyRegistration(address assetProxyContract, bool isRegistered);
|
||||
|
||||
@@ -36,9 +38,15 @@ contract AssetProxyOwner is
|
||||
/// @dev Function will revert if the transaction does not call `removeAuthorizedAddressAtIndex`
|
||||
/// on an approved AssetProxy contract.
|
||||
modifier validRemoveAuthorizedAddressAtIndexTx(uint256 transactionId) {
|
||||
Transaction storage tx = transactions[transactionId];
|
||||
require(isAssetProxyRegistered[tx.destination]);
|
||||
require(readBytes4(tx.data, 0) == REMOVE_AUTHORIZED_ADDRESS_AT_INDEX_SELECTOR);
|
||||
Transaction storage txn = transactions[transactionId];
|
||||
require(
|
||||
isAssetProxyRegistered[txn.destination],
|
||||
"UNREGISTERED_ASSET_PROXY"
|
||||
);
|
||||
require(
|
||||
txn.data.readBytes4(0) == REMOVE_AUTHORIZED_ADDRESS_AT_INDEX_SELECTOR,
|
||||
"INVALID_FUNCTION_SELECTOR"
|
||||
);
|
||||
_;
|
||||
}
|
||||
|
||||
@@ -48,7 +56,7 @@ contract AssetProxyOwner is
|
||||
/// @param _assetProxyContracts Array of AssetProxy contract addresses.
|
||||
/// @param _required Number of required confirmations.
|
||||
/// @param _secondsTimeLocked Duration needed after a transaction is confirmed and before it becomes executable, in seconds.
|
||||
function AssetProxyOwner(
|
||||
constructor (
|
||||
address[] memory _owners,
|
||||
address[] memory _assetProxyContracts,
|
||||
uint256 _required,
|
||||
@@ -59,7 +67,10 @@ contract AssetProxyOwner is
|
||||
{
|
||||
for (uint256 i = 0; i < _assetProxyContracts.length; i++) {
|
||||
address assetProxy = _assetProxyContracts[i];
|
||||
require(assetProxy != address(0));
|
||||
require(
|
||||
assetProxy != address(0),
|
||||
"INVALID_ASSET_PROXY"
|
||||
);
|
||||
isAssetProxyRegistered[assetProxy] = true;
|
||||
}
|
||||
}
|
||||
@@ -74,7 +85,7 @@ contract AssetProxyOwner is
|
||||
notNull(assetProxyContract)
|
||||
{
|
||||
isAssetProxyRegistered[assetProxyContract] = isRegistered;
|
||||
AssetProxyRegistration(assetProxyContract, isRegistered);
|
||||
emit AssetProxyRegistration(assetProxyContract, isRegistered);
|
||||
}
|
||||
|
||||
/// @dev Allows execution of `removeAuthorizedAddressAtIndex` without time lock.
|
||||
@@ -85,35 +96,13 @@ contract AssetProxyOwner is
|
||||
fullyConfirmed(transactionId)
|
||||
validRemoveAuthorizedAddressAtIndexTx(transactionId)
|
||||
{
|
||||
Transaction storage tx = transactions[transactionId];
|
||||
tx.executed = true;
|
||||
// solhint-disable-next-line avoid-call-value
|
||||
if (tx.destination.call.value(tx.value)(tx.data))
|
||||
Execution(transactionId);
|
||||
else {
|
||||
ExecutionFailure(transactionId);
|
||||
tx.executed = false;
|
||||
Transaction storage txn = transactions[transactionId];
|
||||
txn.executed = true;
|
||||
if (external_call(txn.destination, txn.value, txn.data.length, txn.data)) {
|
||||
emit Execution(transactionId);
|
||||
} else {
|
||||
emit ExecutionFailure(transactionId);
|
||||
txn.executed = false;
|
||||
}
|
||||
}
|
||||
|
||||
/// @dev Reads an unpadded bytes4 value from a position in a byte array.
|
||||
/// @param b Byte array containing a bytes4 value.
|
||||
/// @param index Index in byte array of bytes4 value.
|
||||
/// @return bytes4 value from byte array.
|
||||
function readBytes4(
|
||||
bytes memory b,
|
||||
uint256 index
|
||||
)
|
||||
internal
|
||||
returns (bytes4 result)
|
||||
{
|
||||
require(b.length >= index + 4);
|
||||
assembly {
|
||||
result := mload(add(b, 32))
|
||||
// Solidity does not require us to clean the trailing bytes.
|
||||
// We do it anyway
|
||||
result := and(result, 0xFFFFFFFF00000000000000000000000000000000000000000000000000000000)
|
||||
}
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
@@ -37,7 +37,6 @@ contract Exchange is
|
||||
MixinAssetProxyDispatcher,
|
||||
MixinWrapperFunctions
|
||||
{
|
||||
|
||||
string constant public VERSION = "2.0.1-alpha";
|
||||
|
||||
// Mixins are instantiated in the order they are inherited
|
||||
|
@@ -19,7 +19,6 @@
|
||||
pragma solidity 0.4.24;
|
||||
|
||||
import "../../utils/Ownable/Ownable.sol";
|
||||
import "../../utils/LibBytes/LibBytes.sol";
|
||||
import "./mixins/MAssetProxyDispatcher.sol";
|
||||
import "../AssetProxy/interfaces/IAssetProxy.sol";
|
||||
|
||||
@@ -28,8 +27,6 @@ contract MixinAssetProxyDispatcher is
|
||||
Ownable,
|
||||
MAssetProxyDispatcher
|
||||
{
|
||||
using LibBytes for bytes;
|
||||
|
||||
// Mapping from Asset Proxy Id's to their respective Asset Proxy
|
||||
mapping (bytes4 => IAssetProxy) public assetProxies;
|
||||
|
||||
@@ -90,7 +87,7 @@ contract MixinAssetProxyDispatcher is
|
||||
"LENGTH_GREATER_THAN_3_REQUIRED"
|
||||
);
|
||||
|
||||
// Lookup assetProxy
|
||||
// Lookup assetProxy. We do not use `LibBytes.readBytes4` for gas efficiency reasons.
|
||||
bytes4 assetProxyId;
|
||||
assembly {
|
||||
assetProxyId := and(mload(
|
||||
|
@@ -75,7 +75,11 @@ contract MixinExchangeCore is
|
||||
|
||||
// Update orderEpoch
|
||||
orderEpoch[makerAddress][senderAddress] = newOrderEpoch;
|
||||
emit CancelUpTo(makerAddress, senderAddress, newOrderEpoch);
|
||||
emit CancelUpTo(
|
||||
makerAddress,
|
||||
senderAddress,
|
||||
newOrderEpoch
|
||||
);
|
||||
}
|
||||
|
||||
/// @dev Fills the input order.
|
||||
@@ -107,14 +111,7 @@ contract MixinExchangeCore is
|
||||
public
|
||||
nonReentrant
|
||||
{
|
||||
// Fetch current order status
|
||||
OrderInfo memory orderInfo = getOrderInfo(order);
|
||||
|
||||
// Validate context
|
||||
assertValidCancel(order, orderInfo);
|
||||
|
||||
// Perform cancel
|
||||
updateCancelledState(order, orderInfo.orderHash);
|
||||
cancelOrderInternal(order);
|
||||
}
|
||||
|
||||
/// @dev Gets information about an order: status, hash, and amount filled.
|
||||
@@ -231,11 +228,31 @@ contract MixinExchangeCore is
|
||||
);
|
||||
|
||||
// Settle order
|
||||
settleOrder(order, takerAddress, fillResults);
|
||||
settleOrder(
|
||||
order,
|
||||
takerAddress,
|
||||
fillResults
|
||||
);
|
||||
|
||||
return fillResults;
|
||||
}
|
||||
|
||||
/// @dev After calling, the order can not be filled anymore.
|
||||
/// Throws if order is invalid or sender does not have permission to cancel.
|
||||
/// @param order Order to cancel. Order must be OrderStatus.FILLABLE.
|
||||
function cancelOrderInternal(Order memory order)
|
||||
internal
|
||||
{
|
||||
// Fetch current order status
|
||||
OrderInfo memory orderInfo = getOrderInfo(order);
|
||||
|
||||
// Validate context
|
||||
assertValidCancel(order, orderInfo);
|
||||
|
||||
// Perform cancel
|
||||
updateCancelledState(order, orderInfo.orderHash);
|
||||
}
|
||||
|
||||
/// @dev Updates state with results of a fill order.
|
||||
/// @param order that was filled.
|
||||
/// @param takerAddress Address of taker who filled the order.
|
||||
@@ -404,16 +421,6 @@ contract MixinExchangeCore is
|
||||
safeMul(order.makerAssetAmount, takerAssetFilledAmount),
|
||||
"INVALID_FILL_PRICE"
|
||||
);
|
||||
|
||||
// Validate fill order rounding
|
||||
require(
|
||||
!isRoundingErrorFloor(
|
||||
takerAssetFilledAmount,
|
||||
order.takerAssetAmount,
|
||||
order.makerAssetAmount
|
||||
),
|
||||
"ROUNDING_ERROR"
|
||||
);
|
||||
}
|
||||
|
||||
/// @dev Validates context for cancelOrder. Succeeds or throws.
|
||||
@@ -463,17 +470,17 @@ contract MixinExchangeCore is
|
||||
{
|
||||
// Compute proportional transfer amounts
|
||||
fillResults.takerAssetFilledAmount = takerAssetFilledAmount;
|
||||
fillResults.makerAssetFilledAmount = getPartialAmountFloor(
|
||||
fillResults.makerAssetFilledAmount = safeGetPartialAmountFloor(
|
||||
takerAssetFilledAmount,
|
||||
order.takerAssetAmount,
|
||||
order.makerAssetAmount
|
||||
);
|
||||
fillResults.makerFeePaid = getPartialAmountFloor(
|
||||
takerAssetFilledAmount,
|
||||
order.takerAssetAmount,
|
||||
fillResults.makerFeePaid = safeGetPartialAmountFloor(
|
||||
fillResults.makerAssetFilledAmount,
|
||||
order.makerAssetAmount,
|
||||
order.makerFee
|
||||
);
|
||||
fillResults.takerFeePaid = getPartialAmountFloor(
|
||||
fillResults.takerFeePaid = safeGetPartialAmountFloor(
|
||||
takerAssetFilledAmount,
|
||||
order.takerAssetAmount,
|
||||
order.takerFee
|
||||
|
@@ -177,13 +177,13 @@ contract MixinMatchOrders is
|
||||
{
|
||||
// Derive maker asset amounts for left & right orders, given store taker assert amounts
|
||||
uint256 leftTakerAssetAmountRemaining = safeSub(leftOrder.takerAssetAmount, leftOrderTakerAssetFilledAmount);
|
||||
uint256 leftMakerAssetAmountRemaining = getPartialAmountFloor(
|
||||
uint256 leftMakerAssetAmountRemaining = safeGetPartialAmountFloor(
|
||||
leftOrder.makerAssetAmount,
|
||||
leftOrder.takerAssetAmount,
|
||||
leftTakerAssetAmountRemaining
|
||||
);
|
||||
uint256 rightTakerAssetAmountRemaining = safeSub(rightOrder.takerAssetAmount, rightOrderTakerAssetFilledAmount);
|
||||
uint256 rightMakerAssetAmountRemaining = getPartialAmountFloor(
|
||||
uint256 rightMakerAssetAmountRemaining = safeGetPartialAmountFloor(
|
||||
rightOrder.makerAssetAmount,
|
||||
rightOrder.takerAssetAmount,
|
||||
rightTakerAssetAmountRemaining
|
||||
@@ -205,7 +205,7 @@ contract MixinMatchOrders is
|
||||
matchedFillResults.left.takerAssetFilledAmount = matchedFillResults.right.makerAssetFilledAmount;
|
||||
// Round down to ensure the maker's exchange rate does not exceed the price specified by the order.
|
||||
// We favor the maker when the exchange rate must be rounded.
|
||||
matchedFillResults.left.makerAssetFilledAmount = getPartialAmountFloor(
|
||||
matchedFillResults.left.makerAssetFilledAmount = safeGetPartialAmountFloor(
|
||||
leftOrder.makerAssetAmount,
|
||||
leftOrder.takerAssetAmount,
|
||||
matchedFillResults.left.takerAssetFilledAmount
|
||||
@@ -217,7 +217,7 @@ contract MixinMatchOrders is
|
||||
matchedFillResults.right.makerAssetFilledAmount = matchedFillResults.left.takerAssetFilledAmount;
|
||||
// Round up to ensure the maker's exchange rate does not exceed the price specified by the order.
|
||||
// We favor the maker when the exchange rate must be rounded.
|
||||
matchedFillResults.right.takerAssetFilledAmount = getPartialAmountCeil(
|
||||
matchedFillResults.right.takerAssetFilledAmount = safeGetPartialAmountCeil(
|
||||
rightOrder.takerAssetAmount,
|
||||
rightOrder.makerAssetAmount,
|
||||
matchedFillResults.right.makerAssetFilledAmount
|
||||
@@ -231,24 +231,24 @@ contract MixinMatchOrders is
|
||||
);
|
||||
|
||||
// Compute fees for left order
|
||||
matchedFillResults.left.makerFeePaid = getPartialAmountFloor(
|
||||
matchedFillResults.left.makerFeePaid = safeGetPartialAmountFloor(
|
||||
matchedFillResults.left.makerAssetFilledAmount,
|
||||
leftOrder.makerAssetAmount,
|
||||
leftOrder.makerFee
|
||||
);
|
||||
matchedFillResults.left.takerFeePaid = getPartialAmountFloor(
|
||||
matchedFillResults.left.takerFeePaid = safeGetPartialAmountFloor(
|
||||
matchedFillResults.left.takerAssetFilledAmount,
|
||||
leftOrder.takerAssetAmount,
|
||||
leftOrder.takerFee
|
||||
);
|
||||
|
||||
// Compute fees for right order
|
||||
matchedFillResults.right.makerFeePaid = getPartialAmountFloor(
|
||||
matchedFillResults.right.makerFeePaid = safeGetPartialAmountFloor(
|
||||
matchedFillResults.right.makerAssetFilledAmount,
|
||||
rightOrder.makerAssetAmount,
|
||||
rightOrder.makerFee
|
||||
);
|
||||
matchedFillResults.right.takerFeePaid = getPartialAmountFloor(
|
||||
matchedFillResults.right.takerFeePaid = safeGetPartialAmountFloor(
|
||||
matchedFillResults.right.takerAssetFilledAmount,
|
||||
rightOrder.takerAssetAmount,
|
||||
rightOrder.takerFee
|
||||
|
@@ -251,7 +251,7 @@ contract MixinSignatureValidator is
|
||||
walletAddress, // address of Wallet contract
|
||||
cdStart, // pointer to start of input
|
||||
mload(calldata), // length of input
|
||||
cdStart, // write input over output
|
||||
cdStart, // write output over input
|
||||
32 // output size is 32 bytes
|
||||
)
|
||||
|
||||
@@ -301,7 +301,7 @@ contract MixinSignatureValidator is
|
||||
validatorAddress, // address of Validator contract
|
||||
cdStart, // pointer to start of input
|
||||
mload(calldata), // length of input
|
||||
cdStart, // write input over output
|
||||
cdStart, // write output over input
|
||||
32 // output size is 32 bytes
|
||||
)
|
||||
|
||||
|
@@ -28,7 +28,6 @@ contract MixinTransactions is
|
||||
MSignatureValidator,
|
||||
MTransactions
|
||||
{
|
||||
|
||||
// Mapping of transaction hash => executed
|
||||
// This prevents transactions from being executed more than once.
|
||||
mapping (bytes32 => bool) public transactions;
|
||||
@@ -36,15 +35,6 @@ contract MixinTransactions is
|
||||
// Address of current transaction signer
|
||||
address public currentContextAddress;
|
||||
|
||||
// Hash for the EIP712 ZeroEx Transaction Schema
|
||||
bytes32 constant internal EIP712_ZEROEX_TRANSACTION_SCHEMA_HASH = keccak256(abi.encodePacked(
|
||||
"ZeroExTransaction(",
|
||||
"uint256 salt,",
|
||||
"address signerAddress,",
|
||||
"bytes data",
|
||||
")"
|
||||
));
|
||||
|
||||
/// @dev Executes an exchange method call in the context of signer.
|
||||
/// @param salt Arbitrary number to ensure uniqueness of transaction hash.
|
||||
/// @param signerAddress Address of transaction signer.
|
||||
|
@@ -36,7 +36,6 @@ contract MixinWrapperFunctions is
|
||||
MExchangeCore,
|
||||
MWrapperFunctions
|
||||
{
|
||||
|
||||
/// @dev Fills the input order. Reverts if exact takerAssetFillAmount not filled.
|
||||
/// @param order Order struct containing order specifications.
|
||||
/// @param takerAssetFillAmount Desired amount of takerAsset to sell.
|
||||
@@ -82,7 +81,7 @@ contract MixinWrapperFunctions is
|
||||
// Delegate to `fillOrder` and handle any exceptions gracefully
|
||||
assembly {
|
||||
let success := delegatecall(
|
||||
gas, // forward all gas, TODO: look into gas consumption of assert/throw
|
||||
gas, // forward all gas
|
||||
address, // call address of this contract
|
||||
add(fillOrderCalldata, 32), // pointer to start of input (skip array length in first 32 bytes)
|
||||
mload(fillOrderCalldata), // length of input
|
||||
@@ -96,6 +95,7 @@ contract MixinWrapperFunctions is
|
||||
mstore(add(fillResults, 96), mload(add(fillOrderCalldata, 96)))
|
||||
}
|
||||
}
|
||||
// fillResults values will be 0 by default if call was unsuccessful
|
||||
return fillResults;
|
||||
}
|
||||
|
||||
@@ -376,10 +376,11 @@ contract MixinWrapperFunctions is
|
||||
/// @param orders Array of order specifications.
|
||||
function batchCancelOrders(LibOrder.Order[] memory orders)
|
||||
public
|
||||
nonReentrant
|
||||
{
|
||||
uint256 ordersLength = orders.length;
|
||||
for (uint256 i = 0; i != ordersLength; i++) {
|
||||
cancelOrder(orders[i]);
|
||||
cancelOrderInternal(orders[i]);
|
||||
}
|
||||
}
|
||||
|
||||
|
@@ -20,6 +20,7 @@ pragma solidity 0.4.24;
|
||||
|
||||
|
||||
contract LibEIP712 {
|
||||
|
||||
// EIP191 header for EIP712 prefix
|
||||
string constant internal EIP191_HEADER = "\x19\x01";
|
||||
|
||||
|
@@ -24,7 +24,6 @@ import "../../../utils/SafeMath/SafeMath.sol";
|
||||
contract LibFillResults is
|
||||
SafeMath
|
||||
{
|
||||
|
||||
struct FillResults {
|
||||
uint256 makerAssetFilledAmount; // Total amount of makerAsset(s) filled.
|
||||
uint256 takerAssetFilledAmount; // Total amount of takerAsset(s) filled.
|
||||
|
@@ -24,6 +24,83 @@ import "../../../utils/SafeMath/SafeMath.sol";
|
||||
contract LibMath is
|
||||
SafeMath
|
||||
{
|
||||
/// @dev Calculates partial value given a numerator and denominator rounded down.
|
||||
/// Reverts if rounding error is >= 0.1%
|
||||
/// @param numerator Numerator.
|
||||
/// @param denominator Denominator.
|
||||
/// @param target Value to calculate partial of.
|
||||
/// @return Partial value of target rounded down.
|
||||
function safeGetPartialAmountFloor(
|
||||
uint256 numerator,
|
||||
uint256 denominator,
|
||||
uint256 target
|
||||
)
|
||||
internal
|
||||
pure
|
||||
returns (uint256 partialAmount)
|
||||
{
|
||||
require(
|
||||
denominator > 0,
|
||||
"DIVISION_BY_ZERO"
|
||||
);
|
||||
|
||||
require(
|
||||
!isRoundingErrorFloor(
|
||||
numerator,
|
||||
denominator,
|
||||
target
|
||||
),
|
||||
"ROUNDING_ERROR"
|
||||
);
|
||||
|
||||
partialAmount = safeDiv(
|
||||
safeMul(numerator, target),
|
||||
denominator
|
||||
);
|
||||
return partialAmount;
|
||||
}
|
||||
|
||||
/// @dev Calculates partial value given a numerator and denominator rounded down.
|
||||
/// Reverts if rounding error is >= 0.1%
|
||||
/// @param numerator Numerator.
|
||||
/// @param denominator Denominator.
|
||||
/// @param target Value to calculate partial of.
|
||||
/// @return Partial value of target rounded up.
|
||||
function safeGetPartialAmountCeil(
|
||||
uint256 numerator,
|
||||
uint256 denominator,
|
||||
uint256 target
|
||||
)
|
||||
internal
|
||||
pure
|
||||
returns (uint256 partialAmount)
|
||||
{
|
||||
require(
|
||||
denominator > 0,
|
||||
"DIVISION_BY_ZERO"
|
||||
);
|
||||
|
||||
require(
|
||||
!isRoundingErrorCeil(
|
||||
numerator,
|
||||
denominator,
|
||||
target
|
||||
),
|
||||
"ROUNDING_ERROR"
|
||||
);
|
||||
|
||||
// safeDiv computes `floor(a / b)`. We use the identity (a, b integer):
|
||||
// ceil(a / b) = floor((a + b - 1) / b)
|
||||
// To implement `ceil(a / b)` using safeDiv.
|
||||
partialAmount = safeDiv(
|
||||
safeAdd(
|
||||
safeMul(numerator, target),
|
||||
safeSub(denominator, 1)
|
||||
),
|
||||
denominator
|
||||
);
|
||||
return partialAmount;
|
||||
}
|
||||
|
||||
/// @dev Calculates partial value given a numerator and denominator rounded down.
|
||||
/// @param numerator Numerator.
|
||||
@@ -43,7 +120,7 @@ contract LibMath is
|
||||
denominator > 0,
|
||||
"DIVISION_BY_ZERO"
|
||||
);
|
||||
|
||||
|
||||
partialAmount = safeDiv(
|
||||
safeMul(numerator, target),
|
||||
denominator
|
||||
@@ -69,7 +146,7 @@ contract LibMath is
|
||||
denominator > 0,
|
||||
"DIVISION_BY_ZERO"
|
||||
);
|
||||
|
||||
|
||||
// safeDiv computes `floor(a / b)`. We use the identity (a, b integer):
|
||||
// ceil(a / b) = floor((a + b - 1) / b)
|
||||
// To implement `ceil(a / b)` using safeDiv.
|
||||
@@ -128,7 +205,11 @@ contract LibMath is
|
||||
// 1000 * remainder < numerator * target
|
||||
// so we have a rounding error iff:
|
||||
// 1000 * remainder >= numerator * target
|
||||
uint256 remainder = mulmod(target, numerator, denominator);
|
||||
uint256 remainder = mulmod(
|
||||
target,
|
||||
numerator,
|
||||
denominator
|
||||
);
|
||||
isError = safeMul(1000, remainder) >= safeMul(numerator, target);
|
||||
return isError;
|
||||
}
|
||||
@@ -160,8 +241,11 @@ contract LibMath is
|
||||
return false;
|
||||
}
|
||||
// Compute remainder as before
|
||||
uint256 remainder = mulmod(target, numerator, denominator);
|
||||
// TODO: safeMod
|
||||
uint256 remainder = mulmod(
|
||||
target,
|
||||
numerator,
|
||||
denominator
|
||||
);
|
||||
remainder = safeSub(denominator, remainder) % denominator;
|
||||
isError = safeMul(1000, remainder) >= safeMul(numerator, target);
|
||||
return isError;
|
||||
|
@@ -24,7 +24,6 @@ import "./LibEIP712.sol";
|
||||
contract LibOrder is
|
||||
LibEIP712
|
||||
{
|
||||
|
||||
// Hash for the EIP712 Order Schema
|
||||
bytes32 constant internal EIP712_ORDER_SCHEMA_HASH = keccak256(abi.encodePacked(
|
||||
"Order(",
|
||||
|
@@ -24,7 +24,6 @@ import "../interfaces/IAssetProxyDispatcher.sol";
|
||||
contract MAssetProxyDispatcher is
|
||||
IAssetProxyDispatcher
|
||||
{
|
||||
|
||||
// Logs registration of new asset proxy
|
||||
event AssetProxyRegistered(
|
||||
bytes4 id, // Id of new registered AssetProxy.
|
||||
|
@@ -72,6 +72,11 @@ contract MExchangeCore is
|
||||
internal
|
||||
returns (LibFillResults.FillResults memory fillResults);
|
||||
|
||||
/// @dev After calling, the order can not be filled anymore.
|
||||
/// @param order Order struct containing order specifications.
|
||||
function cancelOrderInternal(LibOrder.Order memory order)
|
||||
internal;
|
||||
|
||||
/// @dev Updates state with results of a fill order.
|
||||
/// @param order that was filled.
|
||||
/// @param takerAddress Address of taker who filled the order.
|
||||
|
@@ -26,7 +26,6 @@ import "../interfaces/IMatchOrders.sol";
|
||||
contract MMatchOrders is
|
||||
IMatchOrders
|
||||
{
|
||||
|
||||
/// @dev Validates context for matchOrders. Succeeds or throws.
|
||||
/// @param leftOrder First order to match.
|
||||
/// @param rightOrder Second order to match.
|
||||
|
@@ -23,6 +23,28 @@ import "../interfaces/ITransactions.sol";
|
||||
contract MTransactions is
|
||||
ITransactions
|
||||
{
|
||||
// Hash for the EIP712 ZeroEx Transaction Schema
|
||||
bytes32 constant internal EIP712_ZEROEX_TRANSACTION_SCHEMA_HASH = keccak256(abi.encodePacked(
|
||||
"ZeroExTransaction(",
|
||||
"uint256 salt,",
|
||||
"address signerAddress,",
|
||||
"bytes data",
|
||||
")"
|
||||
));
|
||||
|
||||
/// @dev Calculates EIP712 hash of the Transaction.
|
||||
/// @param salt Arbitrary number to ensure uniqueness of transaction hash.
|
||||
/// @param signerAddress Address of transaction signer.
|
||||
/// @param data AbiV2 encoded calldata.
|
||||
/// @return EIP712 hash of the Transaction.
|
||||
function hashZeroExTransaction(
|
||||
uint256 salt,
|
||||
address signerAddress,
|
||||
bytes memory data
|
||||
)
|
||||
internal
|
||||
pure
|
||||
returns (bytes32 result);
|
||||
|
||||
/// @dev The current function will be called in the context of this address (either 0x transaction signer or `msg.sender`).
|
||||
/// If calling a fill function, this address will represent the taker.
|
||||
|
@@ -24,8 +24,9 @@ import "../libs/LibFillResults.sol";
|
||||
import "../interfaces/IWrapperFunctions.sol";
|
||||
|
||||
|
||||
contract MWrapperFunctions {
|
||||
|
||||
contract MWrapperFunctions is
|
||||
IWrapperFunctions
|
||||
{
|
||||
/// @dev Fills the input order. Reverts if exact takerAssetFillAmount not filled.
|
||||
/// @param order LibOrder.Order struct containing order specifications.
|
||||
/// @param takerAssetFillAmount Desired amount of takerAsset to sell.
|
||||
|
69
packages/contracts/src/2.0.0/test/DummyERC20Token/DummyMultipleReturnERC20Token.sol
vendored
Normal file
69
packages/contracts/src/2.0.0/test/DummyERC20Token/DummyMultipleReturnERC20Token.sol
vendored
Normal file
@@ -0,0 +1,69 @@
|
||||
/*
|
||||
|
||||
Copyright 2018 ZeroEx Intl.
|
||||
|
||||
Licensed under the Apache License, Version 2.0 (the "License");
|
||||
you may not use this file except in compliance with the License.
|
||||
You may obtain a copy of the License at
|
||||
|
||||
http://www.apache.org/licenses/LICENSE-2.0
|
||||
|
||||
Unless required by applicable law or agreed to in writing, software
|
||||
distributed under the License is distributed on an "AS IS" BASIS,
|
||||
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
See the License for the specific language governing permissions and
|
||||
limitations under the License.
|
||||
|
||||
*/
|
||||
|
||||
pragma solidity 0.4.24;
|
||||
|
||||
import "./DummyERC20Token.sol";
|
||||
|
||||
|
||||
// solhint-disable no-empty-blocks
|
||||
contract DummyMultipleReturnERC20Token is
|
||||
DummyERC20Token
|
||||
{
|
||||
constructor (
|
||||
string _name,
|
||||
string _symbol,
|
||||
uint256 _decimals,
|
||||
uint256 _totalSupply
|
||||
)
|
||||
public
|
||||
DummyERC20Token(
|
||||
_name,
|
||||
_symbol,
|
||||
_decimals,
|
||||
_totalSupply
|
||||
)
|
||||
{}
|
||||
|
||||
/// @dev send `value` token to `to` from `from` on the condition it is approved by `from`
|
||||
/// @param _from The address of the sender
|
||||
/// @param _to The address of the recipient
|
||||
/// @param _value The amount of token to be transferred
|
||||
function transferFrom(
|
||||
address _from,
|
||||
address _to,
|
||||
uint256 _value
|
||||
)
|
||||
external
|
||||
returns (bool)
|
||||
{
|
||||
emit Transfer(
|
||||
_from,
|
||||
_to,
|
||||
_value
|
||||
);
|
||||
|
||||
// HACK: This contract will not compile if we remove `returns (bool)`, so we manually return 64 bytes (equiavalent to true, true)
|
||||
assembly {
|
||||
mstore(0, 1)
|
||||
mstore(32, 1)
|
||||
return(0, 64)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@@ -25,7 +25,6 @@ import "./DummyERC20Token.sol";
|
||||
contract DummyNoReturnERC20Token is
|
||||
DummyERC20Token
|
||||
{
|
||||
|
||||
constructor (
|
||||
string _name,
|
||||
string _symbol,
|
||||
|
@@ -24,7 +24,6 @@ import "../../tokens/ERC721Token/IERC721Receiver.sol";
|
||||
contract DummyERC721Receiver is
|
||||
IERC721Receiver
|
||||
{
|
||||
|
||||
// Function selector for ERC721Receiver.onERC721Received
|
||||
// 0x150b7a02
|
||||
bytes4 constant internal ERC721_RECEIVED = bytes4(keccak256("onERC721Received(address,address,uint256,bytes)"));
|
||||
|
@@ -25,10 +25,10 @@ import "../../protocol/Exchange/interfaces/IExchange.sol";
|
||||
import "../../protocol/Exchange/libs/LibOrder.sol";
|
||||
|
||||
|
||||
// solhint-disable no-unused-vars
|
||||
contract ReentrantERC20Token is
|
||||
ERC20Token
|
||||
{
|
||||
|
||||
using LibBytes for bytes;
|
||||
|
||||
// solhint-disable-next-line var-name-mixedcase
|
||||
@@ -50,6 +50,7 @@ contract ReentrantERC20Token is
|
||||
MARKET_SELL_ORDERS,
|
||||
MATCH_ORDERS,
|
||||
CANCEL_ORDER,
|
||||
BATCH_CANCEL_ORDERS,
|
||||
CANCEL_ORDERS_UP_TO,
|
||||
SET_SIGNATURE_VALIDATOR_APPROVAL
|
||||
}
|
||||
@@ -149,6 +150,11 @@ contract ReentrantERC20Token is
|
||||
EXCHANGE.cancelOrder.selector,
|
||||
order
|
||||
);
|
||||
} else if (currentFunctionId == uint8(ExchangeFunction.BATCH_CANCEL_ORDERS)) {
|
||||
calldata = abi.encodeWithSelector(
|
||||
EXCHANGE.batchCancelOrders.selector,
|
||||
orders
|
||||
);
|
||||
} else if (currentFunctionId == uint8(ExchangeFunction.CANCEL_ORDERS_UP_TO)) {
|
||||
calldata = abi.encodeWithSelector(
|
||||
EXCHANGE.cancelOrdersUpTo.selector,
|
||||
|
@@ -16,7 +16,7 @@
|
||||
|
||||
*/
|
||||
|
||||
pragma solidity 0.4.10;
|
||||
pragma solidity 0.4.24;
|
||||
|
||||
import "../../protocol/AssetProxyOwner/AssetProxyOwner.sol";
|
||||
|
||||
@@ -25,8 +25,7 @@ import "../../protocol/AssetProxyOwner/AssetProxyOwner.sol";
|
||||
contract TestAssetProxyOwner is
|
||||
AssetProxyOwner
|
||||
{
|
||||
|
||||
function TestAssetProxyOwner(
|
||||
constructor (
|
||||
address[] memory _owners,
|
||||
address[] memory _assetProxyContracts,
|
||||
uint256 _required,
|
||||
@@ -38,6 +37,7 @@ contract TestAssetProxyOwner is
|
||||
|
||||
function testValidRemoveAuthorizedAddressAtIndexTx(uint256 id)
|
||||
public
|
||||
view
|
||||
validRemoveAuthorizedAddressAtIndexTx(id)
|
||||
returns (bool)
|
||||
{
|
||||
@@ -50,23 +50,9 @@ contract TestAssetProxyOwner is
|
||||
/// @return Successful if data is a call to `removeAuthorizedAddressAtIndex`.
|
||||
function isFunctionRemoveAuthorizedAddressAtIndex(bytes memory data)
|
||||
public
|
||||
pure
|
||||
returns (bool)
|
||||
{
|
||||
return readBytes4(data, 0) == REMOVE_AUTHORIZED_ADDRESS_AT_INDEX_SELECTOR;
|
||||
}
|
||||
|
||||
/// @dev Reads an unpadded bytes4 value from a position in a byte array.
|
||||
/// @param b Byte array containing a bytes4 value.
|
||||
/// @param index Index in byte array of bytes4 value.
|
||||
/// @return bytes4 value from byte array.
|
||||
function publicReadBytes4(
|
||||
bytes memory b,
|
||||
uint256 index
|
||||
)
|
||||
public
|
||||
returns (bytes4 result)
|
||||
{
|
||||
result = readBytes4(b, index);
|
||||
return result;
|
||||
return data.readBytes4(0) == REMOVE_AUTHORIZED_ADDRESS_AT_INDEX_SELECTOR;
|
||||
}
|
||||
}
|
||||
|
@@ -62,6 +62,42 @@ contract TestExchangeInternals is
|
||||
return calculateFillResults(order, takerAssetFilledAmount);
|
||||
}
|
||||
|
||||
/// @dev Calculates partial value given a numerator and denominator.
|
||||
/// Reverts if rounding error is >= 0.1%
|
||||
/// @param numerator Numerator.
|
||||
/// @param denominator Denominator.
|
||||
/// @param target Value to calculate partial of.
|
||||
/// @return Partial value of target.
|
||||
function publicSafeGetPartialAmountFloor(
|
||||
uint256 numerator,
|
||||
uint256 denominator,
|
||||
uint256 target
|
||||
)
|
||||
public
|
||||
pure
|
||||
returns (uint256 partialAmount)
|
||||
{
|
||||
return safeGetPartialAmountFloor(numerator, denominator, target);
|
||||
}
|
||||
|
||||
/// @dev Calculates partial value given a numerator and denominator.
|
||||
/// Reverts if rounding error is >= 0.1%
|
||||
/// @param numerator Numerator.
|
||||
/// @param denominator Denominator.
|
||||
/// @param target Value to calculate partial of.
|
||||
/// @return Partial value of target.
|
||||
function publicSafeGetPartialAmountCeil(
|
||||
uint256 numerator,
|
||||
uint256 denominator,
|
||||
uint256 target
|
||||
)
|
||||
public
|
||||
pure
|
||||
returns (uint256 partialAmount)
|
||||
{
|
||||
return safeGetPartialAmountCeil(numerator, denominator, target);
|
||||
}
|
||||
|
||||
/// @dev Calculates partial value given a numerator and denominator.
|
||||
/// @param numerator Numerator.
|
||||
/// @param denominator Denominator.
|
||||
|
@@ -31,7 +31,6 @@ contract TestLibs is
|
||||
LibFillResults,
|
||||
LibAbiEncoder
|
||||
{
|
||||
|
||||
function publicAbiEncodeFillOrder(
|
||||
Order memory order,
|
||||
uint256 takerAssetFillAmount,
|
||||
|
@@ -26,7 +26,6 @@ contract TestSignatureValidator is
|
||||
MixinSignatureValidator,
|
||||
MixinTransactions
|
||||
{
|
||||
|
||||
function publicIsValidSignature(
|
||||
bytes32 hash,
|
||||
address signer,
|
||||
|
@@ -24,7 +24,6 @@ import "./IERC20Token.sol";
|
||||
contract ERC20Token is
|
||||
IERC20Token
|
||||
{
|
||||
|
||||
mapping (address => uint256) internal balances;
|
||||
mapping (address => mapping (address => uint256)) internal allowed;
|
||||
|
||||
|
@@ -26,7 +26,6 @@ contract MintableERC20Token is
|
||||
SafeMath,
|
||||
UnlimitedAllowanceERC20Token
|
||||
{
|
||||
|
||||
/// @dev Mints new tokens
|
||||
/// @param _to Address of the beneficiary that will own the minted token
|
||||
/// @param _value Amount of tokens to mint
|
||||
|
@@ -24,7 +24,6 @@ import "../ERC20Token/ERC20Token.sol";
|
||||
contract UnlimitedAllowanceERC20Token is
|
||||
ERC20Token
|
||||
{
|
||||
|
||||
uint256 constant internal MAX_UINT = 2**256 - 1;
|
||||
|
||||
/// @dev ERC20 transferFrom, modified such that an allowance of MAX_UINT represents an unlimited allowance. See https://github.com/ethereum/EIPs/issues/717
|
||||
|
@@ -24,7 +24,6 @@ import "./ERC721Token.sol";
|
||||
contract MintableERC721Token is
|
||||
ERC721Token
|
||||
{
|
||||
|
||||
/// @dev Function to mint a new token
|
||||
/// Reverts if the given token ID already exists
|
||||
/// @param _to Address of the beneficiary that will own the minted token
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user