delete packages

This commit is contained in:
Lawrence Forman 2020-10-07 16:11:19 -04:00
parent 0571244e9e
commit 40dc10729b
1150 changed files with 0 additions and 124445 deletions

View File

@ -1,10 +0,0 @@
# Blacklist all files
.*
*
# Whitelist lib
!lib/**/*
# Blacklist tests and publish scripts
/lib/test/*
/lib/monorepo_scripts/
# Package specific ignore
!_bundles/**/*

File diff suppressed because it is too large Load Diff

View File

@ -1,727 +0,0 @@
<!--
changelogUtils.file is auto-generated using the monorepo-scripts package. Don't edit directly.
Edit the package's CHANGELOG.json file only.
-->
CHANGELOG
## v9.2.0 - _July 15, 2020_
* Export `GethCallOverrides` type (#2620)
* Export `ExchangeProxyMetaTransaction` and `SignedExchangeProxyMetaTransaction` (#2610)
## v9.1.6 - _June 24, 2020_
* Dependencies updated
## v9.1.5 - _March 3, 2020_
* Dependencies updated
## v9.1.4 - _February 27, 2020_
* Dependencies updated
## v9.1.3 - _February 26, 2020_
* Dependencies updated
## v9.1.2 - _February 25, 2020_
* Dependencies updated
## v9.1.1 - _February 15, 2020_
* Dependencies updated
## v9.1.0 - _February 8, 2020_
* Export `EvmBytecodeOutputLinkReferences` (#2462)
## v9.0.7 - _February 6, 2020_
* Dependencies updated
## v9.0.6 - _February 4, 2020_
* Dependencies updated
## v9.0.5 - _January 23, 2020_
* Dependencies updated
## v9.0.4 - _January 22, 2020_
* Update exports. (#2432)
## v9.0.3 - _January 6, 2020_
* Dependencies updated
## v9.0.2 - _December 17, 2019_
* Dependencies updated
## v9.0.1 - _December 9, 2019_
* Dependencies updated
## v9.0.0 - _December 2, 2019_
* Remove ZRXToken contract wrapper (#2324)
* ContractWrappers no longer exposes `erc20Proxy`, `erc721Proxy` and `dutchAuction` wrappers (#2324)
* [Breaking] Big refactor of contract wrapper interface. See https://github.com/0xProject/0x-monorepo/pull/2325 for details (#2325)
* Remove IWallet and IValidator contract wrappers (#2337)
* Remove exports orderHashUtils and transactionHashUtils (#2321)
* Update BigNumber version to ~9.0.0 (#2342)
* Exported intefaces changed: from getContractAddressesForNetworkOrThrow to getContractAddressesForChainOrThrow, from NetworkId to ChainId, from ContractNetworks to ContractChains, and from ContractNetworkData to ContractChainData. (#2313)
* Updated to work with 0x v3
## v8.0.0-beta.3 - _December 2, 2019_
* Dependencies updated
## v8.0.0-beta.2 - _November 20, 2019_
* Dependencies updated
## v8.0.0-beta.1 - _November 17, 2019_
* Remove ZRXToken contract wrapper (#2324)
* ContractWrappers no longer exposes `erc20Proxy`, `erc721Proxy` and `dutchAuction` wrappers (#2324)
* [Breaking] Big refactor of contract wrapper interface. See https://github.com/0xProject/0x-monorepo/pull/2325 for details (#2325)
* Remove IWallet and IValidator contract wrappers (#2337)
* Remove exports orderHashUtils and transactionHashUtils (#2321)
* Update BigNumber version to ~9.0.0 (#2342)
## v8.0.0-beta.0 - _November 7, 2019_
* Exported intefaces changed: from getContractAddressesForNetworkOrThrow to getContractAddressesForChainOrThrow, from NetworkId to ChainId, from ContractNetworks to ContractChains, and from ContractNetworkData to ContractChainData. (#2313)
## v7.1.0-beta.0 - _October 3, 2019_
* Updated to work with 0x v3
## v7.0.2 - _September 17, 2019_
* Dependencies updated
## v7.0.1 - _September 3, 2019_
* Dependencies updated
## v7.0.0 - _August 22, 2019_
* Add optional `exchangeAddress` parameter to `signatureUtils.isValidSignatureAsync` to fix `Validator` type signatures. (#2017)
* Removed @0x/order-watcher
* Update to latest @0x/contract-wrappers v11 (#2068)
## v6.0.15 - _August 8, 2019_
* Dependencies updated
## v6.0.14 - _July 31, 2019_
* Dependencies updated
## v6.0.13 - _July 24, 2019_
* re-export new ethereum-types type, TupleDataItem (#1919)
## v6.0.12 - _July 15, 2019_
* Dependencies updated
## v6.0.11 - _July 13, 2019_
* Dependencies updated
## v6.0.10 - _July 13, 2019_
* Dependencies updated
## v6.0.9 - _May 15, 2019_
* Dependencies updated
## v6.0.8 - _May 14, 2019_
* Dependencies updated
## v6.0.7 - _May 10, 2019_
* Dependencies updated
## v6.0.6 - _April 11, 2019_
* Dependencies updated
## v6.0.5 - _March 21, 2019_
* Dependencies updated
## v6.0.4 - _March 20, 2019_
* Dependencies updated
## v6.0.3 - _March 1, 2019_
* Dependencies updated
## v6.0.2 - _February 27, 2019_
* Dependencies updated
## v6.0.1 - _February 26, 2019_
* Dependencies updated
## v6.0.0 - _February 25, 2019_
* Add support for EIP1193 providers & Web3.js providers >= 1.0-beta.38 (#1627)
* Update provider params to type SupportedProvider which outlines all supported providers (#1627)
## v5.0.0 - _February 9, 2019_
* Export `transactionHashUtils`, `DecodedCalldata`, `ZeroExTransaction`, and `SignedZeroExTransaction` (#1569)
## v4.0.3 - _February 7, 2019_
* Dependencies updated
## v4.0.2 - _February 7, 2019_
* Dependencies updated
## v4.0.1 - _February 6, 2019_
* Dependencies updated
## v4.0.0 - _February 5, 2019_
* Upgrade the bignumber.js to v8.0.2 (#1517)
## v3.0.3 - _January 17, 2019_
* Dependencies updated
## v3.0.2 - _January 15, 2019_
* Dependencies updated
## v3.0.1 - _January 11, 2019_
* Dependencies updated
## v3.0.0 - _January 9, 2019_
* Export `MultiAssetData`, `MultiAssetDataWithRecursiveDecoding`, `ObjectMap`, and `SingleAssetData` from types. No longer export `AssetData`. (#1363)
## v2.0.8 - _December 13, 2018_
* Dependencies updated
## v2.0.7 - _December 11, 2018_
* Dependencies updated
## v2.0.6 - _November 28, 2018_
* Dependencies updated
## v2.0.5 - _November 21, 2018_
* Dependencies updated
## v2.0.4 - _November 14, 2018_
* Dependencies updated
## v2.0.3 - _November 13, 2018_
* Dependencies updated
## v2.0.2 - _November 12, 2018_
* Dependencies updated
## v2.0.1 - _November 9, 2018_
* Dependencies updated
## v2.0.0 - _October 18, 2018_
* Add support for `eth_signTypedData`. (#1102)
* Added `MetamaskSubprovider` to handle inconsistencies in Metamask's signing JSON RPC endpoints. (#1102)
* Removed `SignerType` (including `SignerType.Metamask`). Please use the `MetamaskSubprovider` to wrap `web3.currentProvider`. (#1102)
* Updated to use new modularized artifacts and the latest version of @0xproject/contract-wrappers (#1105)
* Make web3-provider-engine types a 'dependency' so it's available to users of the library (#1105)
* Export new `AssetData` type from types (#1131)
## v1.0.8 - _October 4, 2018_
* Dependencies updated
## v1.0.7 - _September 28, 2018_
* Dependencies updated
## v1.0.6 - _September 25, 2018_
* Dependencies updated
## v1.0.5 - _September 25, 2018_
* Dependencies updated
## 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
## v1.0.1-rc.5 - _Invalid date_
* Fix `main` and `types` package.json entries so that they point to the new location of index.d.ts and index.js
## v1.0.1-rc.4 - _August 24, 2018_
* Re-organize the exported interface of 0x.js. Remove the `ZeroEx` class, and instead export the same exports as `0x.js`'s sub-packages: `@0xproject/contract-wrappers`, `@0xproject/order-utils` and `@0xproject/order-watcher` (#963)
## v1.0.1-rc.3 - _August 14, 2018_
* Dependencies updated
* Update ecSignOrderHashAsync to return the signature as a string for immediate use in contracts (#914)
## v1.0.1-rc.2 - _July 26, 2018_
* Fixed bug caused by importing non-existent dep
## v1.0.1-rc.1 - _July 26, 2018_
* Dependencies updated
## v1.0.0 - _July 23, 2018_
* Dependencies updated
## v1.0.0-rc.2 - _July 19, 2018_
* Remove `zeroEx.assetData` and instead re-export it's static functions directly off `ZeroEx`
## v1.0.0-rc.1 - _July 19, 2018_
* Remove tokenRegistry wrapper (#863)
* Rename `zeroEx.token` to `zeroEx.erc20Token`, and add `zeroEx.erc721Token` (#863)
* Rename `zeroEx.proxy` to `zeroEx.erc20Proxy` and add `zeroEx.erc721Proxy` (#863)
* Refactored `ZeroEx.isValidSignature` to `zeroEx.isValidSignatureAsync`. It is now async so that it can verify contract-dependent signature types (#863)
* Refactored `signOrderHashAsync` to `ecSignOrderHashAsync`. There are now many non-ECSignature ways to sign orders too. (#863)
* Removed `createOrderWatcherAsync` method. Will be added back once OrderWatcher is refactored for V2 (#863)
* 0x.js exports renamed contract events and event arg types (#863)
* Export `ZeroEx.assetData` with methods to decode/encode assetData fields found in 0x orders (#884)
## v0.38.6 - _July 18, 2018_
* Dependencies updated
## v0.38.5 - _July 9, 2018_
* Dependencies updated
## v0.38.4 - _June 19, 2018_
* Dependencies updated
## v0.38.3 - _May 29, 2018_
* Dependencies updated
## v0.38.2 - _May 29, 2018_
* Dependencies updated
## v0.38.1 - _May 29, 2018_
* Dependencies updated
## v0.38.0 - _May 22, 2018_
* Renamed createOrderStateWatcher to createOrderWatcherAsync since it is now async (#579)
* Renamed ZeroExError to ContractWrappersErrors since they now lives in the @0xproject/contract-wrappers subpackage (#579)
## v0.37.2 - _May 4, 2018_
* Dependencies updated
## v0.37.1 - _May 4, 2018_
* Dependencies updated
## v0.37.0 - _May 4, 2018_
* Fixed expiration watcher comparator to handle orders with equal expiration times (#526)
* Update Web3 Provider Engine to 14.0.4 (#555)
* Add `zeroEx.getProvider()` (#559)
* Move `ZeroExError.InvalidSignature` to `@0xproject/order-utils` `OrderError.InvalidSignature` (#559)
## v0.36.3 - _April 18, 2018_
* Move @0xproject/migrations to devDependencies
## v0.36.2 - _April 18, 2018_
* Dependencies updated
## v0.36.1 - _April 18, 2018_
* Internal changes and refactoring
* Fix redundant expired order removal bug (#527)
## v0.36.0 - _April 11, 2018_
* Moved Web3.Provider to `@0xproject/types:Provider` (#501)
* Add `zeroEx.exchange.getOrderStateAsync` to allow obtaining current OrderState for a signedOrder (#510)
## v0.35.0 - _April 2, 2018_
* Removed `ZeroExError.TransactionMiningTimeout` and moved it to '@0xproject/web3-wrapper' `Web3WrapperErrors.TransactionMiningTimeout` (#485)
## v0.34.0 - _April 2, 2018_
* Fix the bug causing `zeroEx.exchange.fillOrdersUpToAsync` validation to fail if there were some extra orders passed (#470)
* Remove automatic instantiation of `zeroEx.orderStateWatcher` (#488)
* Add `zeroEx.createOrderStateWatcher` to allow creating arbitrary number of OrderStateWatchers (#488)
* Added `stateLayer` setting to `OrderStateWatcherConfig` so OrderStateWatcher can be set to monitor different blockchain state layers (#488)
## v0.33.2 - _March 17, 2018_
* Consolidate all `console.log` calls into `logUtils` in the `@0xproject/utils` package (#452)
* Consolidate `Order`, `SignedOrder`, and `ECSignature` into the `@0xproject/types` package (#456)
## v0.33.1 - _March 7, 2018_
* Add missing EthersJs typescript typings as dependency
## v0.33.0 - _March 3, 2018_
* Validate and lowercase all addresses in public methods (#373)
* Improve validation to force passing contract addresses on private networks (#385)
* Change `LogErrorContractEventArgs.errorId` type from `BigNumber` to `number` (#413)
* Rename all public `_unsubscribeAll` methods to `unsubscribeAll` (#415)
* Move web3 typings from devDep to dep since cannot use this package without it (#429)
## v0.32.2 - _February 8, 2018_
* Fix publishing issue where .npmignore was not properly excluding undesired content (#389)
## v0.32.1 - _February 6, 2018_
* Reorganized `BlockParamLiteral` export into `@0xproject/types` package (#355)
* Now using `abi-gen` package to generate ContractEventArgs types (#371)
## v0.32.0 - _February 4, 2018_
* Add `zeroEx.etherToken.getContractAddressIfExists` (#350)
* Fixed the bug causing order watcher to throw if there is an event with the same signature but different indexed fields (#366)
## v0.31.1 - _January 31, 2018_
* Fix the bug causing order watcher to throw if makerToken === zrx (#357)
## v0.31.0 - _January 29, 2018_
* Add the `shouldAddPersonalMessagePrefix` parameter to `signOrderHashAsync` so that the caller can decide on whether to add the personalMessage prefix before relaying the request to the signer. Parity Signer, Ledger and TestRPC add the prefix themselves, Metamask expects it to have already been added. (#349)
## v0.30.2 - _January 28, 2018_
* Add Rinkeby testnet addresses to artifacts (#337)
* Move @0xproject/types to dependencies from devDependencies fixing missing type errors
## v0.30.1 - _January 23, 2018_
* Fix a bug allowing negative fill values (#212)
* Fix a bug that made it impossible to pass a custom ZRX address (#341)
## v0.30.0 - _January 16, 2018_
* Add an error parameter to the order watcher callback (#312)
* Fix a bug making it impossible to catch some errors from awaitTransactionMinedAsync (#312)
* Fix a bug in fillOrdersUpTo validation making it impossible to fill up to if user doesn't have enough balance to fully fill all the orders (#321)
## v0.29.1 - _January 10, 2018_
* Fixed bignumber config issue #301 (#305)
## v0.29.0 - _December 27, 2017_
* Assert baseUnit amount supplied to `toUnitAmount` is integer amount. (#287)
* `toBaseUnitAmount` throws if amount supplied has too many decimals (#287)
## v0.28.0 - _December 19, 2017_
* Add `etherTokenAddress` arg to `depositAsync` and `withdrawAsync` methods on `zeroEx.etherToken` (#267)
* Removed accidentally included `unsubscribeAll` method from `zeroEx.proxy`, `zeroEx.etherToken` and `zeroEx.tokenRegistry` (#267)
* Removed `etherTokenContractAddress` from `ZeroEx` constructor arg `ZeroExConfig` (#267)
* Rename `SubscriptionOpts` to `BlockRange` (#272)
* Add `zeroEx.etherToken.subscribe`, `zeroEx.etherToken.unsubscribe`, `zeroEx.etherToken.unsubscribeAll` (#277)
* Add `zeroEx.etherToken.getLogsAsync` (#277)
* Add new public types `BlockParamLiteral`, `EtherTokenEvents`, `EtherTokenContractEventArgs`, `DepositContractEventArgs`, `WithdrawalContractEventArgs` (#277)
* Support `Deposit` and `Withdraw` events on etherToken (#277)
* Improve the error message when taker is not a string (#278)
## v0.27.1 - _November 27, 2017_
* Export `TransactionOpts` type
## v0.27.0 - _November 27, 2017_
* Make `ZeroExConfig` required parameter of `ZeroEx` constructor (#233)
* Add a required property `networkId` to `ZeroExConfig` (#233)
* Make all `getContractAddress` functions, `zeroEx.exchange.subscribe`, `zeroEx.exchange.getZRXTokenAddress` sync (#233)
* Remove `ZeroExError.ContractNotFound` and replace it with contract-specific errors (#233)
* Make `DecodedLogEvent<A>` contain `LogWithDecodedArgs<A>` under log key instead of merging it in like web3 does (#234)
* Rename `removed` to `isRemoved` in `DecodedLogEvent<A>` (#234)
* Add config allowing to specify gasPrice and gasLimit for every transaction sending method (#235)
* All transaction sending methods now call `estimateGas` if no gas amount was supplied (#235)
* Modify order validation methods to validate against the `latest` block, not against the `pending` block (#236)
## v0.26.0 - _November 20, 2017_
* Add post-formatter for logs converting `blockNumber`, `logIndex`, `transactionIndex` from hexes to numbers (#231)
* Remove support for Async callback types when used in Subscribe functions (#222)
* In OrderWatcher subscribe to ZRX Token Transfer and Approval events when maker token is different (#225)
## v0.25.1 - _November 12, 2017_
* Standardise on Cancelled over Canceled (#217)
* Add missing `DecodedLogEvent` type to exported types (#205)
* Normalized the transactionReceipt status to be `null|0|1`, 1 meaning transaction execution successful, 0 unsuccessful and `null` if it is a pre-byzantinium transaction. (#200)
## v0.23.0 - _November 11, 2017_
* Fixed unhandled promise rejection error in subscribe methods (#209)
* Subscribe callbacks now receive an error object as their first argument
## v0.22.6 - _November 9, 2017_
* Add a timeout parameter to transaction awaiting (#206)
## v0.22.5 - _November 6, 2017_
* Re-publish v0.22.4 to fix publishing issue
## v0.22.4 - _October 24, 2017_
* Upgraded bignumber.js to a new version that ships with native typings
## v0.22.3 - _October 24, 2017_
* Fixed an issue with new version of testrpc and unlimited proxy allowance (#199)
## v0.22.2 - _October 23, 2017_
* Fixed rounding of maker fill amount and incorrect validation of partial fees (#197)
## v0.22.0 - _October 15, 2017_
* Started using `OrderFillRequest` interface instead of `OrderFillOrKillRequest` interface for `zeroEx.exchange.batchFillOrKill` (#187)
* Removed `OrderFillOrKillRequest` (#187)
## v0.21.4 - _October 12, 2017_
* Made 0x.js more type-safe by making `getLogsAsync` and `subscribe/subscribeAsync` generics parametrized with arg type (#194)
## v0.21.3 - _October 11, 2017_
* Fixed a bug causing order fills to throw `INSUFFICIENT_TAKER_ALLOWANCE` (#193)
## v0.21.2 - _October 10, 2017_
* Exported `ContractEventArg` as a public type (#190)
## v0.21.1 - _October 10, 2017_
* Fixed a bug in subscriptions (#189)
## v0.21.0 - _October 9, 2017_
* Complete rewrite of subscription logic (#182)
* Subscriptions no longer return historical logs. If you want them - use `getLogsAsync`
* Subscriptions now use [ethereumjs-blockstream](https://github.com/ethereumjs/ethereumjs-blockstream) under the hood
* Subscriptions correctly handle block re-orgs (forks)
* Subscriptions correctly backfill logs (connection problems)
* They no longer setup filters on the underlying nodes, so you can use them with infura without a filter Subprovider
* Removed `ContractEventEmitter` and added `LogEvent`
* Renamed `zeroEx.token.subscribeAsync` to `zeroEx.token.subscribe`
* Added `zeroEx.token.unsubscribe` and `zeroEx.exchange.unsubscribe`
* Renamed `zeroEx.exchange.stopWatchingAllEventsAsync` to `zeroEx.exhange.unsubscribeAll`
* Renamed `zeroEx.token.stopWatchingAllEventsAsync` to `zeroEx.token.unsubscribeAll`
* Fixed the batch fills validation by emulating all balance & proxy allowance changes (#185)
## v0.20.0 - _October 4, 2017_
* Add `zeroEx.token.getLogsAsync` (#178)
* Add `zeroEx.exchange.getLogsAsync` (#178)
* Fixed fees validation when one of the tokens transferred is ZRX (#181)
## v0.19.0 - _September 28, 2017_
* Made order validation optional (#172)
* Added Ropsten testnet support (#173)
* Fixed a bug causing awaitTransactionMinedAsync to DDos backend nodes (#175)
## v0.18.0 - _September 25, 2017_
* Added `zeroEx.exchange.validateOrderFillableOrThrowAsync` to simplify orderbook pruning (#170)
## v0.17.0 - _September 25, 2017_
* Made `zeroEx.exchange.getZRXTokenAddressAsync` public (#171)
## v0.16.0 - _September 19, 2017_
* Added the ability to specify custom contract addresses to be used with 0x.js (#165)
* ZeroExConfig.exchangeContractAddress
* ZeroExConfig.tokenRegistryContractAddress
* ZeroExConfig.etherTokenContractAddress
* Added `zeroEx.tokenRegistry.getContractAddressAsync` (#165)
## v0.15.0 - _September 7, 2017_
* Added the ability to specify a historical `blockNumber` at which to query the blockchain's state when calling a token or exchange method (#161)
## v0.14.2 - _September 6, 2017_
* Fixed an issue with bignumber.js types not found (#160)
## v0.14.1 - _September 6, 2017_
* Fixed an issue with Artifact type not found (#159)
## v0.14.0 - _September 5, 2017_
* Added `zeroEx.exchange.throwLogErrorsAsErrors` method to public interface (#157)
* Fixed an issue with overlapping async intervals in `zeroEx.awaitTransactionMinedAsync` (#157)
* Fixed an issue with log decoder returning `BigNumber`s as `strings` (#157)
## v0.13.0 - _September 5, 2017_
* Made all the functions submitting transactions to the network to immediately return transaction hash (#151)
* Added `zeroEx.awaitTransactionMinedAsync` (#151)
* Added `TransactionReceiptWithDecodedLogs`, `LogWithDecodedArgs`, `DecodedLogArgs` to public types (#151)
* Added signature validation to `validateFillOrderThrowIfInvalidAsync` (#152)
## v0.12.1 - _September 1, 2017_
* Added the support for web3@1.x.x provider (#142)
* Added the optional `zeroExConfig` parameter to the constructor of `ZeroEx` (#139)
* Added the ability to specify `gasPrice` when instantiating `ZeroEx` (#139)
## v0.11.0 - _August 23, 2017_
* Added `zeroEx.token.setUnlimitedProxyAllowanceAsync` (#137)
* Added `zeroEx.token.setUnlimitedAllowanceAsync` (#137)
* Added `zeroEx.token.UNLIMITED_ALLOWANCE_IN_BASE_UNITS` (#137)
## v0.10.4 - _August 23, 2017_
* Fixed a bug where checksummed addresses were being pulled from artifacts and not lower-cased. (#135)
## v0.10.1 - _August 23, 2017_
* Added `zeroEx.exchange.validateFillOrderThrowIfInvalidAsync` (#128)
* Added `zeroEx.exchange.validateFillOrKillOrderThrowIfInvalidAsync` (#128)
* Added `zeroEx.exchange.validateCancelOrderThrowIfInvalidAsync` (#128)
* Added `zeroEx.exchange.isRoundingErrorAsync` (#128)
* Added `zeroEx.proxy.getContractAddressAsync` (#130)
* Added `zeroEx.tokenRegistry.getTokenAddressesAsync` (#132)
* Added `zeroEx.tokenRegistry.getTokenAddressBySymbolIfExistsAsync` (#132)
* Added `zeroEx.tokenRegistry.getTokenAddressByNameIfExistsAsync` (#132)
* Added `zeroEx.tokenRegistry.getTokenBySymbolIfExistsAsync` (#132)
* Added `zeroEx.tokenRegistry.getTokenByNameIfExistsAsync` (#132)
* Added clear error message when checksummed address is passed to a public method (#124)
* Fixes the description of `shouldThrowOnInsufficientBalanceOrAllowance` in docs (#127)
## v0.9.3 - _August 21, 2017_
* Update contract artifacts to include latest Kovan and Mainnet deploys (#118)
## v0.9.2 - _August 20, 2017_
* *This version was unpublished because of a publishing issue.*
* Update contract artifacts to include latest Kovan and Mainnet deploys (#118)
## v0.9.1 - _August 15, 2017_
* Fixed the bug causing `zeroEx.token.getBalanceAsync()` to fail if no addresses available (#120)
## v0.9.0 - _July 25, 2017_
* Migrated to the new version of smart contracts (#101)
* Removed the ability to call methods on multiple authorized Exchange smart contracts (#106)
* Made `zeroEx.getOrderHashHex` a static method (#107)
* Cached `net_version` requests and invalidate the cache on calls to `setProvider` (#95)
* Renamed `zeroEx.exchange.batchCancelOrderAsync` to `zeroEx.exchange.batchCancelOrdersAsync`
* Renamed `zeroEx.exchange.batchFillOrderAsync` to `zeroEx.exchange.batchFillOrdersAsync`
* Updated to typescript v2.4 (#104)
* Fixed an issue with incorrect balance/allowance validation when ZRX is one of the tokens traded (#109)
## v0.8.0 - _July 3, 2017_
* Added the ability to call methods on different authorized versions of the Exchange smart contract (#82)
* Updated contract artifacts to reflect latest changes to the smart contracts (0xproject/contracts#59)
* Added `zeroEx.proxy.isAuthorizedAsync` and `zeroEx.proxy.getAuthorizedAddressesAsync` (#89)
* Added `zeroEx.token.subscribeAsync` (#90)
* Made contract invalidation functions private (#90)
* `zeroEx.token.invalidateContractInstancesAsync`
* `zeroEx.exchange.invalidateContractInstancesAsync`
* `zeroEx.proxy.invalidateContractInstance`
* `zeroEx.tokenRegistry.invalidateContractInstance`
* Fixed the bug where `zeroEx.setProviderAsync` didn't invalidate etherToken contract's instance
## v0.7.1 - _June 25, 2017_
* Added the ability to convert Ether to wrapped Ether tokens and back via `zeroEx.etherToken.depostAsync` and `zeroEx.etherToken.withdrawAsync` (#81)
## v0.7.0 - _June 21, 2017_
* Added Kovan smart contract artifacts (#78)
* Started returning fillAmount from `fillOrderAsync` and `fillUpToAsync` (#72)
* Started returning cancelledAmount from `cancelOrderAsync` (#72)
* Renamed type `LogCancelArgs` to `LogCancelContractEventArgs` and `LogFillArgs` to `LogFillContractEventArgs`
## v0.6.2 - _June 20, 2017_
* Reduced bundle size
* Improved documentation
## v0.6.1 - _June 18, 2017_
* Improved documentation
## v0.6.0 - _June 18, 2017_
* Made `ZeroEx` class accept `Web3Provider` instance instead of `Web3` instance
* Added types for contract event arguments
## v0.5.2 - _June 14, 2017_
* Fixed the bug in `postpublish` script that caused that only unminified UMD bundle was uploaded to release page
## v0.5.1 - _June 14, 2017_
* Added `postpublish` script to publish to Github Releases with assets.

View File

@ -1,129 +0,0 @@
## 0x.js
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 asset-data-utils.
### Read the [Documentation](https://0x.org/docs/tools/0x.js).
## Installation
0x.js ships as both a [UMD](https://github.com/umdjs/umd) module and a [CommonJS](https://en.wikipedia.org/wiki/CommonJS) package.
#### CommonJS _(recommended)_:
**Install**
```bash
npm install 0x.js --save
```
**Import**
```javascript
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`:
```json
"compilerOptions": {
"typeRoots": ["node_modules/@0x/typescript-typings/types", "node_modules/@types"],
}
```
#### UMD:
**Install**
Download the UMD module from our [releases page](https://github.com/0xProject/0x-monorepo/releases) and add it to your project.
**Import**
```html
<script type="text/javascript" src="0x.js"></script>
```
#### Webpack config
If bundling your project with [Webpack](https://webpack.js.org/), add the following to your `webpack.config.js`:
If building for web:
```js
node: {
fs: 'empty';
}
```
If building a node library:
```js
externals: {
fs: true;
}
```
`ContractWrappers` uses WebAssembly to simulate Ethereum calls. This toolchain involves generated 'glue' code that requires the `fs` built-in, but won't actually use it in a web environment. We tell Webpack not to resolve them since we won't need them. The specific dependency is [here](https://github.com/ethereumjs/rustbn.js/blob/master/lib/index.asm.js).
Also see:
- https://webpack.js.org/configuration/externals
- https://webpack.js.org/configuration/node
## Contributing
We strongly recommend that the community help us make improvements and determine the future direction of 0x protocol. To report bugs within this package, please create an issue in this repository.
Please read our [contribution guidelines](../../CONTRIBUTING.md) before getting started.
### Install dependencies
If you don't have yarn workspaces enabled (Yarn < v1.0) - enable them:
```bash
yarn config set workspaces-experimental true
```
Then install dependencies
```bash
yarn install
```
### Build
To build this package and all other monorepo packages that it depends on, run the following from the monorepo root directory:
```bash
PKG=0x.js yarn build
```
Or continuously rebuild on change:
```bash
PKG=0x.js yarn watch
```
### Clean
```bash
yarn clean
```
### Lint
```bash
yarn lint
```
### Run Tests
```bash
yarn test
```

File diff suppressed because it is too large Load Diff

View File

@ -1,101 +0,0 @@
{
"name": "0x.js",
"version": "9.2.0",
"engines": {
"node": ">=6.12"
},
"description": "A javascript library for interacting with the 0x protocol",
"keywords": [
"0x.js",
"0xproject",
"ethereum",
"tokens",
"exchange"
],
"main": "lib/index.js",
"types": "lib/index.d.ts",
"scripts": {
"build": "yarn build:all",
"build:ci": "yarn build:commonjs",
"build:all": "run-p build:umd:prod build:commonjs",
"lint": "tslint --format stylish --project .",
"fix": "tslint --fix --format stylish --project .",
"test:circleci": "run-s test:coverage",
"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",
"clean": "shx rm -rf _bundles lib test_temp src/generated_contract_wrappers generated_docs",
"build:umd:prod": "NODE_ENV=production node --max_old_space_size=8192 ../../node_modules/.bin/webpack --mode production",
"build:commonjs": "tsc -b",
"diff_docs": "git diff --exit-code ./docs",
"s3:sync_md_docs": "aws s3 sync ./docs s3://docs-markdown/${npm_package_name}/v${npm_package_version} --profile 0xproject --region us-east-1 --grants read=uri=http://acs.amazonaws.com/groups/global/AllUsers",
"docs:md": "ts-doc-gen --sourceDir='$PROJECT_FILES' --output=$MD_FILE_DIR --fileExtension=mdx --tsconfig=./typedoc-tsconfig.json",
"docs:json": "typedoc --excludePrivate --excludeExternals --excludeProtected --ignoreCompilerErrors --target ES5 --tsconfig typedoc-tsconfig.json --json $JSON_FILE_PATH $PROJECT_FILES"
},
"config": {
"postpublish": {
"assets": [
"packages/0x.js/_bundles/index.js",
"packages/0x.js/_bundles/index.min.js"
]
}
},
"repository": {
"type": "git",
"url": "https://github.com/0xProject/0x-monorepo"
},
"license": "Apache-2.0",
"devDependencies": {
"@0x/contract-addresses": "^4.11.0",
"@0x/dev-utils": "^3.3.0",
"@0x/migrations": "^6.4.0",
"@0x/ts-doc-gen": "^0.0.22",
"@0x/tslint-config": "^4.1.0",
"@types/lodash": "4.14.104",
"@types/mocha": "^5.2.7",
"@types/sinon": "^2.2.2",
"awesome-typescript-loader": "^5.2.1",
"chai": "^4.0.1",
"chai-as-promised": "^7.1.0",
"chai-bignumber": "^3.0.0",
"copyfiles": "^2.0.0",
"dirty-chai": "^2.0.1",
"make-promises-safe": "^1.1.0",
"mocha": "^6.2.0",
"npm-run-all": "^4.1.2",
"nyc": "^11.0.1",
"opn-cli": "^3.1.0",
"shx": "^0.2.2",
"sinon": "^4.0.0",
"source-map-support": "^0.5.0",
"terser-webpack-plugin": "^2.0.1",
"tslint": "5.11.0",
"typedoc": "^0.15.0",
"typescript": "3.0.1",
"uglifyjs-webpack-plugin": "^2.0.1",
"webpack": "^4.20.2"
},
"dependencies": {
"@0x/abi-gen-wrappers": "^5.4.0-beta.3",
"@0x/assert": "^3.0.9",
"@0x/asset-swapper": "^4.6.0",
"@0x/base-contract": "^6.2.3",
"@0x/contract-wrappers": "^13.8.0",
"@0x/order-utils": "^10.3.0",
"@0x/subproviders": "^6.1.1",
"@0x/types": "^3.2.0",
"@0x/typescript-typings": "^5.1.1",
"@0x/utils": "^5.5.1",
"@0x/web3-wrapper": "^7.2.0",
"@types/node": "12.12.54",
"@types/web3-provider-engine": "^14.0.0",
"ethereum-types": "^3.2.0",
"ethers": "~4.0.4",
"lodash": "^4.17.11",
"web3-provider-engine": "14.0.6"
},
"publishConfig": {
"access": "public"
},
"gitHead": "4f91bfd907996b2f4dd383778b50c479c2602b56"
}

View File

@ -1,140 +0,0 @@
export { getContractAddressesForChainOrThrow, ChainId, ContractAddresses } from '@0x/contract-addresses';
export { signatureUtils, generatePseudoRandomSalt, assetDataUtils } from '@0x/order-utils';
export {
ExchangeEventArgs,
ExchangeEvents,
ExchangeSignatureValidatorApprovalEventArgs,
ExchangeFillEventArgs,
ExchangeCancelEventArgs,
ExchangeCancelUpToEventArgs,
ExchangeAssetProxyRegisteredEventArgs,
ExchangeContract,
DevUtilsContract,
WETH9EventArgs,
WETH9Events,
WETH9ApprovalEventArgs,
WETH9TransferEventArgs,
WETH9DepositEventArgs,
WETH9WithdrawalEventArgs,
WETH9Contract,
ERC20TokenEventArgs,
ERC20TokenEvents,
ERC20TokenTransferEventArgs,
ERC20TokenApprovalEventArgs,
ERC20TokenContract,
ERC721TokenEventArgs,
ERC721TokenEvents,
ERC721TokenTransferEventArgs,
ERC721TokenApprovalEventArgs,
ERC721TokenApprovalForAllEventArgs,
ERC721TokenContract,
ExchangeOwnershipTransferredEventArgs,
ExchangeProtocolFeeCollectorAddressEventArgs,
ExchangeProtocolFeeMultiplierEventArgs,
ExchangeTransactionExecutionEventArgs,
} from '@0x/contract-wrappers';
export {
ContractEvent,
SendTransactionOpts,
AwaitTransactionSuccessOpts,
ContractFunctionObj,
ContractTxFunctionObj,
SubscriptionErrors,
} from '@0x/base-contract';
export import Web3ProviderEngine = require('web3-provider-engine');
export {
RPCSubprovider,
Callback,
JSONRPCRequestPayloadWithMethod,
ErrorCallback,
MetamaskSubprovider,
} from '@0x/subproviders';
export { DecodedCalldata, BigNumber } from '@0x/utils';
export {
Order,
SignedOrder,
ECSignature,
AssetData,
SingleAssetData,
ERC20AssetData,
ERC20BridgeAssetData,
ERC721AssetData,
ERC1155AssetData,
MultiAssetData,
StaticCallAssetData,
MultiAssetDataWithRecursiveDecoding,
SignatureType,
ZeroExTransaction,
SignedZeroExTransaction,
ValidatorSignature,
SimpleContractArtifact,
SimpleStandardContractOutput,
SimpleEvmOutput,
SimpleEvmBytecodeOutput,
EIP712DomainWithDefaultSchema,
EventCallback,
IndexedFilterValues,
DecodedLogEvent,
ExchangeProxyMetaTransaction,
SignedExchangeProxyMetaTransaction,
} from '@0x/types';
export {
BlockRange,
ContractAbi,
ContractEventArg,
SupportedProvider,
JSONRPCRequestPayload,
JSONRPCResponsePayload,
JSONRPCResponseError,
AbiDefinition,
FunctionAbi,
EventAbi,
EventParameter,
MethodAbi,
ConstructorAbi,
FallbackAbi,
DataItem,
TupleDataItem,
ConstructorStateMutability,
StateMutability,
Web3JsProvider,
GanacheProvider,
EIP1193Provider,
ZeroExProvider,
EIP1193Event,
JSONRPCErrorCallback,
Web3JsV1Provider,
Web3JsV2Provider,
Web3JsV3Provider,
TxData,
ContractArtifact,
CallData,
GethCallOverrides,
BlockParam,
CompilerOpts,
StandardContractOutput,
ContractChains,
TxDataPayable,
BlockParamLiteral,
CompilerSettings,
ContractChainData,
DevdocOutput,
EvmOutput,
CompilerSettingsMetadata,
OptimizerSettings,
OutputField,
ParamDescription,
EvmBytecodeOutput,
EvmBytecodeOutputLinkReferences,
RevertErrorAbi,
DecodedLogArgs,
LogWithDecodedArgs,
} from 'ethereum-types';

View File

@ -1,8 +0,0 @@
{
"extends": "../../tsconfig",
"compilerOptions": {
"outDir": "lib",
"rootDir": "src"
},
"include": ["./src/**/*"]
}

View File

@ -1,3 +0,0 @@
{
"extends": ["@0x/tslint-config"]
}

View File

@ -1,7 +0,0 @@
{
"extends": "../../typedoc-tsconfig",
"compilerOptions": {
"outDir": "lib"
},
"include": ["./src/**/*"]
}

View File

@ -1,70 +0,0 @@
/**
* This is to generate the umd bundle only
*/
const _ = require('lodash');
const TerserPlugin = require('terser-webpack-plugin');
const path = require('path');
const production = process.env.NODE_ENV === 'production';
let entry = {
index: './src/index.ts',
};
if (production) {
entry = _.assign({}, entry, { 'index.min': './src/index.ts' });
}
module.exports = {
entry,
mode: 'production',
output: {
path: path.resolve(__dirname, '_bundles'),
filename: '[name].js',
libraryTarget: 'umd',
library: 'ZeroEx',
umdNamedDefine: true,
},
resolve: {
extensions: ['.ts', '.js', '.json'],
},
devtool: 'source-map',
optimization: {
minimizer: [
new TerserPlugin({
sourceMap: true,
terserOptions: {
mangle: {
reserved: ['BigNumber'],
},
},
}),
],
},
// This supports the ethereumjs-vm dependency in `@0x/base-contract`
// The .wasm 'glue' code generated by Emscripten requires these node builtins,
// but won't actually use them in a web environment. We tell Webpack to not resolve those
// require statements since we know we won't need them.
externals: {
fs: true,
},
module: {
rules: [
{
test: /\.ts$/,
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,
},
},
],
exclude: /node_modules/,
},
],
},
};

View File

@ -1,10 +0,0 @@
# Blacklist all files
.*
*
# Whitelist lib
!lib/**/*
# Blacklist tests and publish scripts
/lib/test/*
/lib/monorepo_scripts/
# Package specific ignore
!bin/**/*

View File

@ -1,928 +0,0 @@
[
{
"version": "5.4.0",
"changes": [
{
"note": "Allow overriding of `data` with contract calls and transactions",
"pr": 2626
}
]
},
{
"timestamp": 1594788383,
"version": "5.3.1",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "5.3.0",
"changes": [
{
"note": "Allow identifiers with leading underscores in python wrappers",
"pr": 2591
}
],
"timestamp": 1592969527
},
{
"version": "5.2.2",
"changes": [
{
"note": "Include `bin` files"
}
],
"timestamp": 1582677073
},
{
"timestamp": 1582623685,
"version": "5.2.1",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "5.2.0",
"changes": [
{
"note": "Support deploying contracts with unliked libraries through `deployWithLibrariesFrom0xArtifactAsync()`",
"pr": 2463
},
{
"note": "Update reference outputs",
"pr": 2466
}
],
"timestamp": 1581204851
},
{
"timestamp": 1580988106,
"version": "5.1.2",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1580811564,
"version": "5.1.1",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "5.1.0",
"changes": [
{
"note": "Catch empty call reverts on live networks.",
"pr": 2433
},
{
"note": "Regenerate test outputs.",
"pr": 2433
}
],
"timestamp": 1579682890
},
{
"timestamp": 1578272714,
"version": "5.0.3",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1576540892,
"version": "5.0.2",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1575931811,
"version": "5.0.1",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "5.0.0",
"changes": [
{
"note": "Refactored TS wrapper templates to result in a more succint interface. See https://github.com/0xProject/0x-monorepo/pull/2325 for details.",
"pr": 2284
},
{
"note": "Python: Corrected return types and values for call() interface to generated method wrappers. (Fixes #2298)",
"pr": 2345
},
{
"note": "Python: Stopped generating send_transaction() interface for constant (view/pure) methods",
"pr": 2345
},
{
"note": "Python: Added a build_transaction() interface to contract method classes",
"pr": 2345
},
{
"note": "Python: Removed `validator` argument to contract method classes for methods that don't have any inputs",
"pr": 2345
},
{
"note": "Python: Changed the names of generated tuples to use the `internalType` field in the ABI, if it's present, resulting in human readable struct names rather than hashes of component field names.",
"pr": 2345
},
{
"note": "Moved shared logic into `BaseContract` helpers to reduce size.",
"pr": 2343
},
{
"note": "Re-enable gas estimation when `gas` is not provided.",
"pr": 2343
},
{
"note": "In Python wrappers, accept string arguments to bytes parameters",
"pr": 2284
},
{
"note": "In Python wrappers, support module-local, Web3.py-compatible middleware",
"pr": 2284
},
{
"note": "In Python wrappers, allow contracts to be instantiated with EITHER a Web3.py BaseProvider OR a Web3 client object",
"pr": 2284
},
{
"note": "In Python wrappers, fix bug with casting some bytes objects using bytes.fromhex()",
"pr": 2284
},
{
"note": "Add `getSelector` method to all functions",
"pr": 2224
},
{
"note": "Command-line argument network-id has changed to chain-id",
"pr": 2313
},
{
"note": "Fix templates not being included in published tarball",
"pr": 2315
}
],
"timestamp": 1575296764
},
{
"version": "4.4.0-beta.4",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1575290197
},
{
"version": "4.4.0-beta.3",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1574238768
},
{
"version": "4.4.0-beta.2",
"changes": [
{
"note": "Refactored TS wrapper templates to result in a more succint interface. See https://github.com/0xProject/0x-monorepo/pull/2325 for details.",
"pr": 2284
},
{
"note": "Python: Corrected return types and values for call() interface to generated method wrappers. (Fixes #2298)",
"pr": 2345
},
{
"note": "Python: Stopped generating send_transaction() interface for constant (view/pure) methods",
"pr": 2345
},
{
"note": "Python: Added a build_transaction() interface to contract method classes",
"pr": 2345
},
{
"note": "Python: Removed `validator` argument to contract method classes for methods that don't have any inputs",
"pr": 2345
},
{
"note": "Python: Changed the names of generated tuples to use the `internalType` field in the ABI, if it's present, resulting in human readable struct names rather than hashes of component field names.",
"pr": 2345
},
{
"note": "Moved shared logic into `BaseContract` helpers to reduce size.",
"pr": 2343
},
{
"note": "Re-enable gas estimation when `gas` is not provided.",
"pr": 2343
}
],
"timestamp": 1574030254
},
{
"version": "4.4.0-beta.1",
"changes": [
{
"note": "In Python wrappers, accept string arguments to bytes parameters",
"pr": 2284
},
{
"note": "In Python wrappers, support module-local, Web3.py-compatible middleware",
"pr": 2284
},
{
"note": "In Python wrappers, allow contracts to be instantiated with EITHER a Web3.py BaseProvider OR a Web3 client object",
"pr": 2284
},
{
"note": "In Python wrappers, fix bug with casting some bytes objects using bytes.fromhex()",
"pr": 2284
},
{
"note": "Add `getSelector` method to all functions",
"pr": 2224
},
{
"note": "Command-line argument network-id has changed to chain-id",
"pr": 2313
},
{
"note": "Fix templates not being included in published tarball",
"pr": 2315
}
],
"timestamp": 1573159180
},
{
"version": "4.3.0-beta.0",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1570135330
},
{
"version": "4.2.1",
"changes": [
{
"note": "Redirect to `evmExecAsync` to use local EVM instead of eth_call for pure functions",
"pr": 2108
}
],
"timestamp": 1568744790
},
{
"version": "4.2.0",
"changes": [
{
"note": "Provide a default set of templates for code generation, used when --template and --partials are left unspecified",
"pr": 2082
}
],
"timestamp": 1567521715
},
{
"timestamp": 1566446343,
"version": "4.1.1",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "4.1.0",
"changes": [
{
"note": "Updated expected typescript output for cli tests to include `getABIDecodedTransactionData` and `getABIDecodedReturnData`",
"pr": 2018
},
{
"note": "Added tests for`getABIDecodedTransactionData` and `getABIDecodedReturnData` in contract wrappers.",
"pr": 2018
}
],
"timestamp": 1565296576
},
{
"version": "4.0.0",
"changes": [
{
"note": "whitespace changes to generated Python code",
"pr": 1996
},
{
"note": "move Python Validator base class from generated code to common package",
"pr": 1996
},
{
"note": "Changed fundamental thing-to-be-wrapped from the contract to the contract method. That is, now there is a base contract method wrapper class rather than a base contract wrapper class, and individual contract methods are represented by named classes inheriting from that base, and the different operations on a method are now represented by a nested-object dot notation, ie, WrappedContract.ContractMethod.call() and WrappedContract.ContractMethod.send_transaction().",
"pr": 1996
},
{
"note": "added gas estimation functionality to contract methods",
"pr": 1996
},
{
"note": "Python: fixed bug with methods returning multiple values",
"pr": 1996
},
{
"note": "Python: fixed bug with methods returning arrays of structs",
"pr": 1996
},
{
"note": "Python: fixed bug with methods that return a struct that contains another struct where the inner struct was not otherwise directly referenced by any method",
"pr": 1996
},
{
"note": "Python: fixed bug with tuples sometimes being used before they were declared",
"pr": 1996
},
{
"note": "Python: fixed bug with supporting overloaded methods",
"pr": 1996
}
]
},
{
"version": "3.1.2",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1564604963
},
{
"version": "3.1.1",
"changes": [
{
"note": "Python method parameters are now in snake case",
"pr": 1919
},
{
"note": "Python wrappers now support tuples in method parameters",
"pr": 1919
},
{
"note": "document Python method's bytes params as requiring UTF-8",
"pr": 1919
},
{
"note": "generate Python output into a contract-named folder, not a file (eg exchange/__init__.py rather than exchange.py) leaving space for user-defined additions to the same module, such as for custom types, as used by the Exchange wrapper's manually-written type aliases in the contract_wrappers.exchange.types Python module",
"pr": 1919
},
{
"note": "support for customizable parameter validation for Python wrappers",
"pr": 1919
},
{
"note": "wrap Python docstrings better, for pydocstyle compliance",
"pr": 1919
},
{
"note": "lots of fixes to satisfy linters of generated Python code",
"pr": 1919
}
],
"timestamp": 1563957393
},
{
"timestamp": 1563047529,
"version": "2.1.1",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "2.1.0",
"changes": [
{
"note": "Initial support for Python",
"pr": 1878
}
],
"timestamp": 1563006338
},
{
"version": "2.0.11",
"changes": [
{
"note": "Watch template files for changes",
"pr": 1875
}
]
},
{
"timestamp": 1557507213,
"version": "2.0.10",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "2.0.9",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1554997931
},
{
"timestamp": 1553183790,
"version": "2.0.8",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1553091633,
"version": "2.0.7",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1551479279,
"version": "2.0.6",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1551220833,
"version": "2.0.5",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1551130135,
"version": "2.0.4",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1549733923,
"version": "2.0.3",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "2.0.2",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1549547375
},
{
"timestamp": 1549452781,
"version": "2.0.1",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "2.0.0",
"changes": [
{
"note": "Upgrade the bignumber.js to v8.0.2",
"pr": 1517
}
],
"timestamp": 1549373905
},
{
"timestamp": 1547561734,
"version": "1.0.22",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1547225310,
"version": "1.0.21",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1547040760,
"version": "1.0.20",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "1.0.19",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1544739608
},
{
"version": "1.0.18",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1544570656
},
{
"timestamp": 1542821676,
"version": "1.0.17",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1542208198,
"version": "1.0.16",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "1.0.15",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1541740904
},
{
"timestamp": 1539871071,
"version": "1.0.14",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "1.0.13",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1538693146
},
{
"timestamp": 1538157789,
"version": "1.0.12",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1537907159,
"version": "1.0.11",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1537875740,
"version": "1.0.10",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"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",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1535133899,
"version": "1.0.6",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1534210131,
"version": "1.0.5",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1532619515,
"version": "1.0.4",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1532614997,
"version": "1.0.3",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1532605697,
"version": "1.0.2",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "1.0.1",
"changes": [
{
"note": "Fix the abi-gen entry point in package.json",
"pr": 901
}
],
"timestamp": 1532357734
},
{
"timestamp": 1532043000,
"version": "1.0.0",
"changes": [
{
"note": "Convert e_r_c to erc in generated file names",
"pr": 822
},
{
"note": "Remove the output directory before writing to it",
"pr": 822
},
{
"note": "skip generation of wrappers that are already up to date",
"pr": 788
}
]
},
{
"timestamp": 1531919263,
"version": "0.3.4",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1531149657,
"version": "0.3.3",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1529397769,
"version": "0.3.2",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "0.3.1",
"changes": [
{
"note": "Incorrect publish that was unpublished"
}
],
"timestamp": 1527810075
},
{
"version": "0.3.0",
"changes": [
{
"note": "Properly export the executable binary",
"pr": 588
}
],
"timestamp": 1527008270
},
{
"timestamp": 1525477860,
"version": "0.2.13",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1525428773,
"version": "0.2.12",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1524044013,
"version": "0.2.11",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1523462196,
"version": "0.2.10",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1522673609,
"version": "0.2.9",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1522658513,
"version": "0.2.8",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "0.2.5",
"changes": [
{
"note": "Consolidate all `console.log` calls into `logUtils` in the `@0xproject/utils` package",
"pr": 452
}
],
"timestamp": 1521298800
},
{
"version": "0.2.4",
"changes": [
{
"note": "Add a `backend` parameter that allows you to specify the Ethereum library you use in your templates (`web3` or `ethers`). Ethers auto-converts small ints to numbers whereas Web3 doesn't. Defaults to `web3`",
"pr": 413
},
{
"note": "Add support for [tuple types](https://solidity.readthedocs.io/en/develop/abi-spec.html#handling-tuple-types)",
"pr": 413
},
{
"note": "Add `hasReturnValue` to context data",
"pr": 413
}
],
"timestamp": 1520089200
},
{
"version": "0.2.1",
"changes": [
{
"note": "Fix publishing issue where .npmignore was not properly excluding undesired content",
"pr": 389
}
],
"timestamp": 1518102000
},
{
"version": "0.2.0",
"changes": [
{
"note": "Added CLI options for explicit specifying location of partials and main template",
"pr": 346
},
{
"note": "Added CLI option to specify networkId, adding support for the JSON artifact format found in @0xproject/contracts",
"pr": 388
}
],
"timestamp": 1517929200
},
{
"version": "0.1.0",
"changes": [
{
"note": "Fixed array typings with union types",
"pr": 295
},
{
"note": "Add event ABIs to context data passed to templates",
"pr": 302
},
{
"note": "Add constructor ABIs to context data passed to templates",
"pr": 304
}
],
"timestamp": 1515596400
}
]

View File

@ -1,365 +0,0 @@
<!--
changelogUtils.file is auto-generated using the monorepo-scripts package. Don't edit directly.
Edit the package's CHANGELOG.json file only.
-->
CHANGELOG
## v5.3.1 - _July 15, 2020_
* Dependencies updated
## v5.3.0 - _June 24, 2020_
* Allow identifiers with leading underscores in python wrappers (#2591)
## v5.2.2 - _February 26, 2020_
* Include `bin` files
## v5.2.1 - _February 25, 2020_
* Dependencies updated
## v5.2.0 - _February 8, 2020_
* Support deploying contracts with unliked libraries through `deployWithLibrariesFrom0xArtifactAsync()` (#2463)
* Update reference outputs (#2466)
## v5.1.2 - _February 6, 2020_
* Dependencies updated
## v5.1.1 - _February 4, 2020_
* Dependencies updated
## v5.1.0 - _January 22, 2020_
* Catch empty call reverts on live networks. (#2433)
* Regenerate test outputs. (#2433)
## v5.0.3 - _January 6, 2020_
* Dependencies updated
## v5.0.2 - _December 17, 2019_
* Dependencies updated
## v5.0.1 - _December 9, 2019_
* Dependencies updated
## v5.0.0 - _December 2, 2019_
* Refactored TS wrapper templates to result in a more succint interface. See https://github.com/0xProject/0x-monorepo/pull/2325 for details. (#2284)
* Python: Corrected return types and values for call() interface to generated method wrappers. (Fixes #2298) (#2345)
* Python: Stopped generating send_transaction() interface for constant (view/pure) methods (#2345)
* Python: Added a build_transaction() interface to contract method classes (#2345)
* Python: Removed `validator` argument to contract method classes for methods that don't have any inputs (#2345)
* Python: Changed the names of generated tuples to use the `internalType` field in the ABI, if it's present, resulting in human readable struct names rather than hashes of component field names. (#2345)
* Moved shared logic into `BaseContract` helpers to reduce size. (#2343)
* Re-enable gas estimation when `gas` is not provided. (#2343)
* In Python wrappers, accept string arguments to bytes parameters (#2284)
* In Python wrappers, support module-local, Web3.py-compatible middleware (#2284)
* In Python wrappers, allow contracts to be instantiated with EITHER a Web3.py BaseProvider OR a Web3 client object (#2284)
* In Python wrappers, fix bug with casting some bytes objects using bytes.fromhex() (#2284)
* Add `getSelector` method to all functions (#2224)
* Command-line argument network-id has changed to chain-id (#2313)
* Fix templates not being included in published tarball (#2315)
## v4.4.0-beta.4 - _December 2, 2019_
* Dependencies updated
## v4.4.0-beta.3 - _November 20, 2019_
* Dependencies updated
## v4.4.0-beta.2 - _November 17, 2019_
* Refactored TS wrapper templates to result in a more succint interface. See https://github.com/0xProject/0x-monorepo/pull/2325 for details. (#2284)
* Python: Corrected return types and values for call() interface to generated method wrappers. (Fixes #2298) (#2345)
* Python: Stopped generating send_transaction() interface for constant (view/pure) methods (#2345)
* Python: Added a build_transaction() interface to contract method classes (#2345)
* Python: Removed `validator` argument to contract method classes for methods that don't have any inputs (#2345)
* Python: Changed the names of generated tuples to use the `internalType` field in the ABI, if it's present, resulting in human readable struct names rather than hashes of component field names. (#2345)
* Moved shared logic into `BaseContract` helpers to reduce size. (#2343)
* Re-enable gas estimation when `gas` is not provided. (#2343)
## v4.4.0-beta.1 - _November 7, 2019_
* In Python wrappers, accept string arguments to bytes parameters (#2284)
* In Python wrappers, support module-local, Web3.py-compatible middleware (#2284)
* In Python wrappers, allow contracts to be instantiated with EITHER a Web3.py BaseProvider OR a Web3 client object (#2284)
* In Python wrappers, fix bug with casting some bytes objects using bytes.fromhex() (#2284)
* Add `getSelector` method to all functions (#2224)
* Command-line argument network-id has changed to chain-id (#2313)
* Fix templates not being included in published tarball (#2315)
## v4.3.0-beta.0 - _October 3, 2019_
* Dependencies updated
## v4.2.1 - _September 17, 2019_
* Redirect to `evmExecAsync` to use local EVM instead of eth_call for pure functions (#2108)
## v4.2.0 - _September 3, 2019_
* Provide a default set of templates for code generation, used when --template and --partials are left unspecified (#2082)
## v4.1.1 - _August 22, 2019_
* Dependencies updated
## v4.1.0 - _August 8, 2019_
* Updated expected typescript output for cli tests to include `getABIDecodedTransactionData` and `getABIDecodedReturnData` (#2018)
* Added tests for`getABIDecodedTransactionData` and `getABIDecodedReturnData` in contract wrappers. (#2018)
## v4.0.0 - _Invalid date_
* whitespace changes to generated Python code (#1996)
* move Python Validator base class from generated code to common package (#1996)
* Changed fundamental thing-to-be-wrapped from the contract to the contract method. That is, now there is a base contract method wrapper class rather than a base contract wrapper class, and individual contract methods are represented by named classes inheriting from that base, and the different operations on a method are now represented by a nested-object dot notation, ie, WrappedContract.ContractMethod.call() and WrappedContract.ContractMethod.send_transaction(). (#1996)
* added gas estimation functionality to contract methods (#1996)
* Python: fixed bug with methods returning multiple values (#1996)
* Python: fixed bug with methods returning arrays of structs (#1996)
* Python: fixed bug with methods that return a struct that contains another struct where the inner struct was not otherwise directly referenced by any method (#1996)
* Python: fixed bug with tuples sometimes being used before they were declared (#1996)
* Python: fixed bug with supporting overloaded methods (#1996)
## v3.1.2 - _July 31, 2019_
* Dependencies updated
## v3.1.1 - _July 24, 2019_
* Python method parameters are now in snake case (#1919)
* Python wrappers now support tuples in method parameters (#1919)
* document Python method's bytes params as requiring UTF-8 (#1919)
* generate Python output into a contract-named folder, not a file (eg exchange/__init__.py rather than exchange.py) leaving space for user-defined additions to the same module, such as for custom types, as used by the Exchange wrapper's manually-written type aliases in the contract_wrappers.exchange.types Python module (#1919)
* support for customizable parameter validation for Python wrappers (#1919)
* wrap Python docstrings better, for pydocstyle compliance (#1919)
* lots of fixes to satisfy linters of generated Python code (#1919)
## v2.1.1 - _July 13, 2019_
* Dependencies updated
## v2.1.0 - _July 13, 2019_
* Initial support for Python (#1878)
## v2.0.11 - _Invalid date_
* Watch template files for changes (#1875)
## v2.0.10 - _May 10, 2019_
* Dependencies updated
## v2.0.9 - _April 11, 2019_
* Dependencies updated
## v2.0.8 - _March 21, 2019_
* Dependencies updated
## v2.0.7 - _March 20, 2019_
* Dependencies updated
## v2.0.6 - _March 1, 2019_
* Dependencies updated
## v2.0.5 - _February 26, 2019_
* Dependencies updated
## v2.0.4 - _February 25, 2019_
* Dependencies updated
## v2.0.3 - _February 9, 2019_
* Dependencies updated
## v2.0.2 - _February 7, 2019_
* Dependencies updated
## v2.0.1 - _February 6, 2019_
* Dependencies updated
## v2.0.0 - _February 5, 2019_
* Upgrade the bignumber.js to v8.0.2 (#1517)
## v1.0.22 - _January 15, 2019_
* Dependencies updated
## v1.0.21 - _January 11, 2019_
* Dependencies updated
## v1.0.20 - _January 9, 2019_
* Dependencies updated
## v1.0.19 - _December 13, 2018_
* Dependencies updated
## v1.0.18 - _December 11, 2018_
* Dependencies updated
## v1.0.17 - _November 21, 2018_
* Dependencies updated
## v1.0.16 - _November 14, 2018_
* Dependencies updated
## v1.0.15 - _November 9, 2018_
* Dependencies updated
## v1.0.14 - _October 18, 2018_
* Dependencies updated
## v1.0.13 - _October 4, 2018_
* Dependencies updated
## v1.0.12 - _September 28, 2018_
* Dependencies updated
## v1.0.11 - _September 25, 2018_
* Dependencies updated
## v1.0.10 - _September 25, 2018_
* Dependencies updated
## v1.0.9 - _September 21, 2018_
* Dependencies updated
## v1.0.8 - _September 5, 2018_
* Dependencies updated
## v1.0.7 - _August 27, 2018_
* Dependencies updated
## v1.0.6 - _August 24, 2018_
* Dependencies updated
## v1.0.5 - _August 14, 2018_
* Dependencies updated
## v1.0.4 - _July 26, 2018_
* Dependencies updated
## v1.0.3 - _July 26, 2018_
* Dependencies updated
## v1.0.2 - _July 26, 2018_
* Dependencies updated
## v1.0.1 - _July 23, 2018_
* Fix the abi-gen entry point in package.json (#901)
## v1.0.0 - _July 19, 2018_
* Convert e_r_c to erc in generated file names (#822)
* Remove the output directory before writing to it (#822)
* skip generation of wrappers that are already up to date (#788)
## v0.3.4 - _July 18, 2018_
* Dependencies updated
## v0.3.3 - _July 9, 2018_
* Dependencies updated
## v0.3.2 - _June 19, 2018_
* Dependencies updated
## v0.3.1 - _May 31, 2018_
* Incorrect publish that was unpublished
## v0.3.0 - _May 22, 2018_
* Properly export the executable binary (#588)
## v0.2.13 - _May 4, 2018_
* Dependencies updated
## v0.2.12 - _May 4, 2018_
* Dependencies updated
## v0.2.11 - _April 18, 2018_
* Dependencies updated
## v0.2.10 - _April 11, 2018_
* Dependencies updated
## v0.2.9 - _April 2, 2018_
* Dependencies updated
## v0.2.8 - _April 2, 2018_
* Dependencies updated
## v0.2.5 - _March 17, 2018_
* Consolidate all `console.log` calls into `logUtils` in the `@0xproject/utils` package (#452)
## v0.2.4 - _March 3, 2018_
* Add a `backend` parameter that allows you to specify the Ethereum library you use in your templates (`web3` or `ethers`). Ethers auto-converts small ints to numbers whereas Web3 doesn't. Defaults to `web3` (#413)
* Add support for [tuple types](https://solidity.readthedocs.io/en/develop/abi-spec.html#handling-tuple-types) (#413)
* Add `hasReturnValue` to context data (#413)
## v0.2.1 - _February 8, 2018_
* Fix publishing issue where .npmignore was not properly excluding undesired content (#389)
## v0.2.0 - _February 6, 2018_
* Added CLI options for explicit specifying location of partials and main template (#346)
* Added CLI option to specify networkId, adding support for the JSON artifact format found in @0xproject/contracts (#388)
## v0.1.0 - _January 10, 2018_
* Fixed array typings with union types (#295)
* Add event ABIs to context data passed to templates (#302)
* Add constructor ABIs to context data passed to templates (#304)

View File

@ -1,152 +0,0 @@
# ABI Gen
This package allows you to generate TypeScript or Python contract wrappers from ABI files.
It's heavily inspired by [Geth abigen](https://github.com/ethereum/go-ethereum/wiki/Native-DApps:-Go-bindings-to-Ethereum-contracts) but takes a different approach.
You can write your custom handlebars templates which will allow you to seamlessly integrate the generated code into your existing codebase with existing conventions.
[Here](https://github.com/0xProject/0x-monorepo/tree/development/packages/0x.js/abi-gen-templates) are the templates used to generate the contract wrappers used by 0x.js.
## Installation
`yarn add -g @0x/abi-gen`
## Usage
```
$ abi-gen --help
Options:
--help Show help [boolean]
--version Show version number [boolean]
--abis Glob pattern to search for ABI JSON files
[string] [required]
--output, -o, --out Folder where to put the output files [string] [required]
--partials Glob pattern for the partial template files [string]
--template Path for the main template file that will be used to
generate each contract [string] [required]
--backend The backing Ethereum library your app uses. For
TypeScript, either 'web3' or 'ethers'. Ethers
auto-converts small ints to numbers whereas Web3 doesn't.
For Python, the only possibility is Web3.py
[string] [choices: "web3", "ethers"] [default: "web3"]
--network-id ID of the network where contract ABIs are nested in
artifacts [number] [default: 50]
--language Language of output file to generate
[string] [choices: "TypeScript", "Python"] [default: "TypeScript"]
Examples:
abi-gen --abis 'src/artifacts/**/*.json' Full usage example
--out 'src/contracts/generated/'
--partials
'src/templates/partials/**/*.handlebars'
--template
'src/templates/contract.handlebars'
```
You're required to pass a [glob](<https://en.wikipedia.org/wiki/Glob_(programming)>) template where your abi files are located.
TL;DR - here is the example from 0x.js.
`--abis 'src/artifacts/@(Exchange|Token|TokenTransferProxy|EtherToken|TokenRegistry).json`
We could've just used `--abis 'src/artifacts/*.json` but we wanted to exclude some of the abi files.
The abi file should be either a [Truffle](http://truffleframework.com/) contract artifact (a JSON object with an abi key) or a JSON abi array.
You need to also specify the location of your main template used for every contract `--template` as well as the partial templates `--partials` that can later be used from the main one.
## How to write custom templates?
The best way to get started is to copy [0x.js templates](https://github.com/0xProject/0x-monorepo/tree/development/packages/abi-gen-templates) and start adjusting them for your needs.
We use [handlebars](http://handlebarsjs.com/) template engine under the hood.
You need to have a master template called `contract.mustache`. it will be used to generate each contract wrapper. Although - you don't need and probably shouldn't write all your logic in a single template file. You can write [partial templates](http://handlebarsjs.com/partials.html) and as long as they are within a partials folder - they will be registered and available.
## Which data/context do I get in my templates?
For now you don't get much on top of methods abi, some useful helpers and a contract name because it was enough for our use-case, but if you need something else - create a PR.
See the [type definition](https://github.com/0xProject/0x-monorepo/tree/development/packages/abi-gen/src/types.ts) of what we pass to the render method.
## Output files
Output files will be generated within the specified output folder. If you already have some files in that folder they will be overwritten.
Names of files, classes and methods will be converted to the standard naming conventions for the given target language.
## Contributing
We welcome improvements and fixes from the wider community! To report bugs within this package, please create an issue in this repository.
Please read our [contribution guidelines](../../CONTRIBUTING.md) before getting started.
### Install dependencies
If you don't have yarn workspaces enabled (Yarn < v1.0) - enable them:
```bash
yarn config set workspaces-experimental true
```
Then install dependencies
```bash
yarn install
```
You will also need to have Python 3 installed in order to build and run the tests of the command-line interface, which is integrated with the `yarn build`, `yarn test`, and `yarn lint` commands described below. More specifically, your local `pip` should resolve to the Python 3 version of `pip`, not a Python 2.x version.
### Build
To build this package and all other monorepo packages that it depends on, run the following from the monorepo root directory:
```bash
PKG=@0x/abi-gen yarn build
```
Or continuously rebuild on change:
```bash
PKG=@0x/abi-gen yarn watch
```
### Clean
```bash
yarn clean
```
### Lint
```bash
yarn lint
```
### CLI tests
The files in `test-cli/` are used to test the output generated by running the command-line tool against a set of fixture contracts. These tests are integrated with `yarn build`, `yarn test`, etc, but can be run independently per the instructions below.
Compile fixture contracts:
```
yarn compile:sol
```
Compiling the fixture contracts into ABI is done ahead of time, and the ABI is checked in to `git`, in order to speed up test run time. Therefore, this compilation does not happen automatically as part of `yarn build`, and must be run explicitly after making any changes to the fixture contracts; and, any proposed changes to the fixture contracts should be accompanied by changes to the corresponding compilation artifacts.
Generate wrappers (and build them, in the case of TypeScript), and build unit tests:
```
yarn test_cli:build
```
Run unit tests and check diffs of generated wrappers vs known wrappers:
```
yarn test_cli
```
Known-good wrappers have been previously committed and are kept in `test-cli/expected-output/{language}`. They are intended to provide sample output and should be kept in sync with the generating code. When making changes to this project or `@0x/abi-gen-templates`, run `yarn test_cli:prebuild` to generate fresh code into `test-cli/output/{language}`, and then manually copy it to `test-cli/expected-output/{language}`.
Run linters against generated code:
```
yarn test_cli:lint
```

View File

@ -1,2 +0,0 @@
#!/usr/bin/env node
require('../lib/src/index.js');

View File

@ -1,28 +0,0 @@
{
"artifactsDir": "./test-cli/fixtures/artifacts",
"contractsDir": "./test-cli/fixtures/contracts",
"useDockerisedSolc": false,
"isOfflineMode": false,
"shouldSaveStandardInput": true,
"compilerSettings": {
"evmVersion": "constantinople",
"optimizer": {
"enabled": true,
"runs": 1000000,
"details": { "yul": true, "deduplicate": true, "cse": true, "constantOptimizer": true }
},
"outputSelection": {
"*": {
"*": [
"abi",
"evm.bytecode.object",
"evm.bytecode.sourceMap",
"evm.deployedBytecode.object",
"evm.deployedBytecode.sourceMap",
"devdoc"
]
}
}
},
"contracts": ["AbiGenDummy.sol", "LibDummy.sol", "TestLibDummy.sol"]
}

View File

@ -1,123 +0,0 @@
{
"name": "@0x/abi-gen",
"version": "5.3.1",
"engines": {
"node": ">=6.12"
},
"description": "Generate contract wrappers from ABI and handlebars templates",
"main": "lib/src/index.js",
"types": "lib/src/index.d.ts",
"scripts": {
"lint": "tslint --format stylish --project .",
"fix": "tslint --fix --format stylish --project . && yarn lint-contracts",
"clean": "shx rm -rf lib && yarn test_cli:clean",
"build": "tsc -b && yarn generate_contract_wrappers && yarn prettier_contract_wrappers && yarn test_cli:build",
"build:ci": "yarn build",
"test": "run-p run_mocha && yarn test_cli",
"test:circleci": "yarn test:coverage && yarn test_cli",
"run_mocha": "(uname -s | grep -q Darwin && echo 'HACK! skipping mocha run due to https://github.com/0xProject/0x-monorepo/issues/2000') || mocha --require source-map-support/register --require make-promises-safe lib/test/*_test.js --timeout 100000 --bail --exit",
"test:coverage": "nyc npm run test --all && yarn coverage:report:lcov",
"coverage:report:lcov": "nyc report --reporter=text-lcov > coverage/lcov.info",
"test_cli": "run-p test_cli:test_typescript diff_contract_wrappers test_cli:lint",
"test_cli:clean": "rm -rf test-cli/test_typescript/lib",
"test_cli:build": "tsc --project test-cli/tsconfig.json",
"test_cli:test_typescript": "mocha --require source-map-support/register --require make-promises-safe test-cli/test_typescript/lib/**/*_test.js --timeout 100000 --bail --exit",
"test_cli:lint": "run-p test_cli:lint_solidity # test_cli:lint_python test_cli:lint_typescript # HACK: typescript and python lint disabled because formatterr fails",
"test_cli:lint_solidity": "solhint -c ../../contracts/.solhint.json test-cli/fixtures/contracts/*.sol",
"test_cli:lint_typescript": "prettier --check ./test-cli/output/typescript/* --config ../../.prettierrc",
"test_cli:lint_python": "pip install -r test-cli/fixtures/python-requirements.txt && run-p test_cli:lint_python:black test_cli:lint_python:mypy test_cli:lint_python:pylint",
"test_cli:lint_python:black": "black --line-length=79 --check ./test-cli/output/python/*",
"test_cli:lint_python:mypy": "MYPYPATH=./stubs mypy ./test-cli/output/python",
"test_cli:lint_python:pylint": "PYTHONPATH=../../python-packages/contract_wrappers/src pylint --rcfile=test-cli/fixtures/pylintrc ./test-cli/output/python/*",
"rebuild_and_test": "run-s build test",
"test:profiler": "SOLIDITY_PROFILER=true run-s build run_mocha profiler:report:html",
"test:trace": "SOLIDITY_REVERT_TRACE=true run-s build run_mocha",
"clean:sol": "rm -rf test-cli/artifacts",
"compile:sol": "sol-compiler",
"watch:sol": "sol-compiler -w",
"prettier_contract_wrappers": "prettier --write ./test-cli/output/typescript/* --config ../../.prettierrc",
"generate_contract_wrappers": "run-p gen_typescript gen_python",
"gen_typescript": "abi-gen --abis ${npm_package_config_abis} --debug --output ./test-cli/output/typescript --backend ethers",
"gen_python": "pip install regex==2019.11.1 && pip install black && abi-gen --abis ${npm_package_config_abis} --output ./test-cli/output/python --language Python",
"diff_contract_wrappers": "git diff --exit-code ./test-cli/output",
"coverage:report:text": "istanbul report text",
"coverage:report:html": "istanbul report html && open coverage/index.html",
"profiler:report:html": "istanbul report html && open coverage/index.html",
"contracts:gen": "contracts-gen generate"
},
"config": {
"abis": "./test-cli/fixtures/artifacts/@(AbiGenDummy|LibDummy|TestLibDummy).json",
"abis:comment": "This list is auto-generated by contracts-gen. Don't edit manually."
},
"bin": {
"abi-gen": "bin/abi-gen.js"
},
"repository": {
"type": "git",
"url": "https://github.com/0xProject/0x-monorepo.git"
},
"license": "Apache-2.0",
"bugs": {
"url": "https://github.com/0xProject/0x-monorepo/issues"
},
"homepage": "https://github.com/0xProject/0x-monorepo/packages/abi-gen/README.md",
"dependencies": {
"@0x/types": "^3.2.0",
"@0x/typescript-typings": "^5.1.1",
"@0x/utils": "^5.5.1",
"@types/toposort": "^2.0.1",
"chalk": "^2.3.0",
"change-case": "^3.0.2",
"cli-format": "^3.0.9",
"ethereum-types": "^3.2.0",
"glob": "^7.1.2",
"handlebars": "^4.1.2",
"lodash": "^4.17.11",
"mkdirp": "^0.5.1",
"tmp": "^0.0.33",
"to-snake-case": "^1.0.0",
"toposort": "^2.0.2",
"yargs": "^10.0.3"
},
"devDependencies": {
"@0x/assert": "^3.0.9",
"@0x/base-contract": "^6.2.3",
"@0x/contracts-gen": "^2.0.10",
"@0x/dev-utils": "^3.3.0",
"@0x/json-schemas": "^5.1.0",
"@0x/sol-compiler": "^4.1.1",
"@0x/subproviders": "^6.1.1",
"@0x/tslint-config": "^4.1.0",
"@0x/web3-wrapper": "^7.2.0",
"@types/glob": "5.0.35",
"@types/mkdirp": "^0.5.2",
"@types/mocha": "^5.2.7",
"@types/node": "12.12.54",
"@types/tmp": "^0.0.33",
"@types/yargs": "^11.0.0",
"chai": "^4.0.1",
"chai-as-promised": "^7.1.0",
"chai-bignumber": "^3.0.0",
"dirty-chai": "^2.0.1",
"ethers": "~4.0.4",
"make-promises-safe": "^1.1.0",
"mocha": "^6.2.0",
"npm-run-all": "^4.1.2",
"shx": "^0.2.2",
"sinon": "^4.0.0",
"solhint": "^1.4.1",
"tslint": "5.11.0",
"typescript": "3.0.1"
},
"publishConfig": {
"access": "public"
},
"files": [
"bin/*",
"templates/*",
"*.js",
"*.ts",
"*.map"
],
"gitHead": "4f91bfd907996b2f4dd383778b50c479c2602b56"
}

View File

@ -1,6 +0,0 @@
declare module '*.json' {
const json: any;
/* tslint:disable */
export default json;
/* tslint:enable */
}

View File

@ -1,303 +0,0 @@
#!/usr/bin/env node
import { AbiEncoder, abiUtils, logUtils } from '@0x/utils';
import chalk from 'chalk';
import * as changeCase from 'change-case';
import { execSync } from 'child_process';
import * as cliFormat from 'cli-format';
import { AbiDefinition, ConstructorAbi, ContractAbi, DevdocOutput, EventAbi, MethodAbi } from 'ethereum-types';
import { sync as globSync } from 'glob';
import * as Handlebars from 'handlebars';
import * as _ from 'lodash';
import * as mkdirp from 'mkdirp';
import * as yargs from 'yargs';
import { registerPythonHelpers } from './python_handlebars_helpers';
import { ContextData, ContractsBackend, ParamKind } from './types';
import { utils } from './utils';
const ABI_TYPE_CONSTRUCTOR = 'constructor';
const ABI_TYPE_METHOD = 'function';
const ABI_TYPE_EVENT = 'event';
const DEFAULT_CHAIN_ID = 1337;
const DEFAULT_BACKEND = 'web3';
const args = yargs
.option('abis', {
describe: 'Glob pattern to search for ABI JSON files',
type: 'string',
demandOption: true,
})
.option('output', {
alias: ['o', 'out'],
describe: 'Folder where to put the output files',
type: 'string',
normalize: true,
demandOption: true,
})
.option('partials', {
describe: 'Glob pattern for the partial template files',
type: 'string',
implies: 'template',
})
.option('template', {
describe:
'Path for the main template file that will be used to generate each contract. Default templates are used based on the --language parameter.',
type: 'string',
normalize: true,
})
.option('backend', {
describe: `The backing Ethereum library your app uses. For TypeScript, either 'web3' or 'ethers'. Ethers auto-converts small ints to numbers whereas Web3 doesn't. For Python, the only possibility is Web3.py`,
type: 'string',
choices: [ContractsBackend.Web3, ContractsBackend.Ethers],
default: DEFAULT_BACKEND,
})
.option('chain-id', {
describe: 'ID of the chain where contract ABIs are nested in artifacts',
type: 'number',
default: DEFAULT_CHAIN_ID,
})
.option('language', {
describe: 'Language of output file to generate',
type: 'string',
choices: ['TypeScript', 'Python'],
default: 'TypeScript',
})
.example(
"$0 --abis 'src/artifacts/**/*.json' --out 'src/contracts/generated/' --debug --partials 'src/templates/partials/**/*.handlebars' --template 'src/templates/contract.handlebars'",
'Full usage example',
).argv;
const templateFilename = args.template || `${__dirname}/../../templates/${args.language}/contract.handlebars`;
const mainTemplate = utils.getNamedContent(templateFilename);
const template = Handlebars.compile<ContextData>(mainTemplate.content);
const abiFileNames = globSync(args.abis);
const partialTemplateFileNames = globSync(
args.partials || `${__dirname}/../../templates/${args.language}/partials/**/*.handlebars`,
);
function registerPartials(): void {
logUtils.log(`Found ${chalk.green(`${partialTemplateFileNames.length}`)} ${chalk.bold('partial')} templates`);
for (const partialTemplateFileName of partialTemplateFileNames) {
const namedContent = utils.getNamedContent(partialTemplateFileName);
Handlebars.registerPartial(namedContent.name, namedContent.content);
}
}
function registerTypeScriptHelpers(): void {
Handlebars.registerHelper('parameterType', utils.solTypeToTsType.bind(utils, ParamKind.Input, args.backend));
Handlebars.registerHelper('assertionType', utils.solTypeToAssertion.bind(utils));
Handlebars.registerHelper('returnType', utils.solTypeToTsType.bind(utils, ParamKind.Output, args.backend));
Handlebars.registerHelper('ifEquals', function(this: typeof Handlebars, arg1: any, arg2: any, options: any): void {
return arg1 === arg2 ? options.fn(this) : options.inverse(this); // tslint:disable-line:no-invalid-this
});
// Check if 0 or false exists
Handlebars.registerHelper(
'isDefined',
(context: any): boolean => {
return context !== undefined;
},
);
// Format docstring for method description
Handlebars.registerHelper(
'formatDocstringForMethodTs',
(docString: string): Handlebars.SafeString => {
// preserve newlines
const regex = /([ ]{4,})+/gi;
const formatted = docString.replace(regex, '\n * ');
return new Handlebars.SafeString(formatted);
},
);
// Get docstring for method param
Handlebars.registerHelper(
'getDocstringForParamTs',
(paramName: string, devdocParamsObj: { [name: string]: string }): Handlebars.SafeString | undefined => {
if (devdocParamsObj === undefined || devdocParamsObj[paramName] === undefined) {
return undefined;
}
return new Handlebars.SafeString(`${devdocParamsObj[paramName]}`);
},
);
// Format docstring for method param
Handlebars.registerHelper(
'formatDocstringForParamTs',
(paramName: string, desc: Handlebars.SafeString): Handlebars.SafeString => {
const docString = `@param ${paramName} ${desc}`;
const hangingIndentLength = 4;
const config = {
width: 80,
paddingLeft: ' * ',
hangingIndent: ' '.repeat(hangingIndentLength),
ansi: false,
};
return new Handlebars.SafeString(`${cliFormat.wrap(docString, config)}`);
},
);
}
if (args.language === 'TypeScript') {
registerTypeScriptHelpers();
} else if (args.language === 'Python') {
registerPythonHelpers();
}
registerPartials();
function makeLanguageSpecificName(methodName: string): string {
if (args.language === 'Python') {
let snakeCased = changeCase.snake(methodName);
// Move leading underscores to the end.
const m = /^(_*).+?(_*)$/.exec(methodName);
if (m) {
snakeCased = `${snakeCased}${m[1] || m[2]}`;
}
return snakeCased;
}
return methodName;
}
if (_.isEmpty(abiFileNames)) {
logUtils.log(`${chalk.red(`No ABI files found.`)}`);
logUtils.log(`Please make sure you've passed the correct folder name and that the files have
${chalk.bold('*.json')} extensions`);
process.exit(1);
} else {
logUtils.log(`Found ${chalk.green(`${abiFileNames.length}`)} ${chalk.bold('ABI')} files`);
mkdirp.sync(args.output);
}
for (const abiFileName of abiFileNames) {
const namedContent = utils.getNamedContent(abiFileName);
logUtils.log(`Processing: ${chalk.bold(namedContent.name)}...`);
const parsedContent = JSON.parse(namedContent.content);
let ABI;
let devdoc: DevdocOutput;
if (_.isArray(parsedContent)) {
ABI = parsedContent; // ABI file
} else if (parsedContent.abi !== undefined) {
ABI = parsedContent.abi; // Truffle artifact
} else if (parsedContent.compilerOutput.abi !== undefined) {
ABI = parsedContent.compilerOutput.abi; // 0x artifact
if (parsedContent.compilerOutput.devdoc !== undefined) {
devdoc = parsedContent.compilerOutput.devdoc;
}
}
if (ABI === undefined) {
logUtils.log(`${chalk.red(`ABI not found in ${abiFileName}.`)}`);
logUtils.log(
`Please make sure your ABI file is either an array with ABI entries or a truffle artifact or 0x sol-compiler artifact`,
);
process.exit(1);
}
const outFileName = utils.makeOutputFileName(namedContent.name);
const outFilePath = (() => {
if (args.language === 'TypeScript') {
return `${args.output}/${outFileName}.ts`;
} else if (args.language === 'Python') {
const directory = `${args.output}/${outFileName}`;
mkdirp.sync(directory);
return `${directory}/__init__.py`;
} else {
throw new Error(`Unexpected language '${args.language}'`);
}
})();
if (utils.isOutputFileUpToDate(outFilePath, [abiFileName, templateFilename, ...partialTemplateFileNames])) {
logUtils.log(`Already up to date: ${chalk.bold(outFilePath)}`);
continue;
}
let deployedBytecode;
try {
deployedBytecode = parsedContent.compilerOutput.evm.deployedBytecode.object;
if (
deployedBytecode === '' ||
deployedBytecode === undefined ||
deployedBytecode === '0x' ||
deployedBytecode === '0x00'
) {
throw new Error();
}
} catch (err) {
logUtils.log(
`Couldn't find deployedBytecode for ${chalk.bold(
namedContent.name,
)}, using undefined. Found [${deployedBytecode}]`,
);
deployedBytecode = undefined;
}
let ctor = ABI.find((abi: AbiDefinition) => abi.type === ABI_TYPE_CONSTRUCTOR) as ConstructorAbi;
if (ctor === undefined) {
ctor = utils.getEmptyConstructor(); // The constructor exists, but it's implicit in JSON's ABI definition
}
const methodAbis = ABI.filter((abi: AbiDefinition) => abi.type === ABI_TYPE_METHOD) as MethodAbi[];
const sanitizedMethodAbis = abiUtils.renameOverloadedMethods(methodAbis) as MethodAbi[];
const methodsData = _.map(methodAbis, (methodAbi, methodAbiIndex: number) => {
_.forEach(methodAbi.inputs, (input, inputIndex: number) => {
if (_.isEmpty(input.name)) {
// Auto-generated getters don't have parameter names
input.name = `index_${inputIndex}`;
}
});
const functionSignature = new AbiEncoder.Method(methodAbi).getSignature();
const languageSpecificName: string = makeLanguageSpecificName(sanitizedMethodAbis[methodAbiIndex].name);
// This will make templates simpler
const methodData = {
...methodAbi,
singleReturnValue: methodAbi.outputs.length === 1,
hasReturnValue: methodAbi.outputs.length !== 0,
languageSpecificName,
functionSignature,
devdoc: devdoc ? devdoc.methods[functionSignature] : undefined,
};
return methodData;
});
const eventAbis = ABI.filter((abi: AbiDefinition) => abi.type === ABI_TYPE_EVENT) as EventAbi[];
const eventsData = _.map(eventAbis, (eventAbi, eventAbiIndex: number) => {
const languageSpecificName = makeLanguageSpecificName(eventAbi.name);
const eventData = {
...eventAbi,
languageSpecificName,
};
return eventData;
});
const shouldIncludeBytecode = methodsData.find(methodData => methodData.stateMutability === 'pure') !== undefined;
const contextData = {
contractName: namedContent.name,
ctor,
deployedBytecode: shouldIncludeBytecode ? deployedBytecode : undefined,
ABI: ABI as ContractAbi,
ABIString: JSON.stringify(ABI),
methods: methodsData,
events: eventsData,
debug: args.debug,
};
const renderedCode = template(contextData);
utils.writeOutputFile(outFilePath, renderedCode);
if (args.language === 'Python') {
// use command-line tool black to reformat, if its available
try {
execSync(`black --line-length 79 ${outFilePath}`);
} catch (e) {
const BLACK_RC_CANNOT_PARSE = 123; // empirical black exit code
if (e.status === BLACK_RC_CANNOT_PARSE) {
logUtils.warn(
'Failed to reformat generated Python with black. Exception thrown by execSync("black ...") follows.',
);
throw e;
} else {
logUtils.warn('Failed to invoke black. Do you have it installed? Proceeding anyways...');
}
}
}
logUtils.log(`Created: ${chalk.bold(outFilePath)}`);
}

View File

@ -1,210 +0,0 @@
import * as changeCase from 'change-case';
import * as cliFormat from 'cli-format';
import * as Handlebars from 'handlebars';
import toposort = require('toposort');
import { AbiDefinition, DataItem, MethodAbi } from 'ethereum-types';
import { utils } from './utils';
/**
* Register all Python-related Handlebars helpers
*/
export function registerPythonHelpers(): void {
Handlebars.registerHelper('equal', (lhs: any, rhs: any) => {
return lhs === rhs;
});
Handlebars.registerHelper('safeString', (str: string) => new Handlebars.SafeString(str));
Handlebars.registerHelper('parameterType', utils.solTypeToPyType.bind(utils));
Handlebars.registerHelper('returnType', utils.solTypeToPyType.bind(utils));
Handlebars.registerHelper('toPythonIdentifier', utils.toPythonIdentifier.bind(utils));
Handlebars.registerHelper('sanitizeDevdocDetails', (_methodName: string, devdocDetails: string, indent: number) => {
// wrap to 80 columns, assuming given indent, so that generated
// docstrings can pass pycodestyle checks. also, replace repeated
// spaces, likely caused by leading indents in the Solidity, because
// they cause repeated spaces in the output, and in particular they may
// cause repeated spaces at the beginning of a line in the docstring,
// which leads to "unexpected indent" errors when generating
// documentation.
if (devdocDetails === undefined || devdocDetails.length === 0) {
return '';
}
const columnsPerRow = 80;
return new Handlebars.SafeString(
`\n${cliFormat.wrap(devdocDetails.replace(/ +/g, ' ') || '', {
paddingLeft: ' '.repeat(indent),
width: columnsPerRow,
ansi: false,
})}\n`,
);
});
Handlebars.registerHelper('makeParameterDocstringRole', (name: string, description: string, indent: number) => {
let docstring = `:param ${name}:`;
if (description && description.length > 0) {
docstring = `${docstring} ${description}`;
}
return new Handlebars.SafeString(utils.wrapPythonDocstringRole(docstring, indent));
});
Handlebars.registerHelper(
'makeReturnDocstringRole',
(description: string, indent: number) =>
new Handlebars.SafeString(
utils.wrapPythonDocstringRole(`:returns: ${description.replace(/ +/g, ' ')}`, indent),
),
);
Handlebars.registerHelper(
'makeEventParameterDocstringRole',
(eventName: string, indent: number) =>
new Handlebars.SafeString(
utils.wrapPythonDocstringRole(
`:param tx_hash: hash of transaction emitting ${eventName} event`,
indent,
),
),
);
Handlebars.registerHelper('tupleDefinitions', (abisJSON: string) => {
const abis: AbiDefinition[] = JSON.parse(abisJSON);
// build an array of objects, each of which has one key, the Python
// name of a tuple, with a string value holding the body of a Python
// class representing that tuple. Using a key-value object conveniently
// filters duplicate references to the same tuple.
const tupleBodies: { [pythonTupleName: string]: string } = {};
// build an array of tuple dependencies, whose format conforms to the
// expected input to toposort, a function to do a topological sort,
// which will help us declare tuples in the proper order, avoiding
// references to tuples that haven't been declared yet.
const tupleDependencies: Array<[string, string]> = [];
for (const abi of abis) {
let parameters: DataItem[] = [];
if (abi.hasOwnProperty('inputs')) {
// HACK(feuGeneA): using "as MethodAbi" below, but abi
// could just as well be ConstructorAbi, EventAbi, etc. We
// just need to tell the TypeScript compiler that it's NOT
// FallbackAbi, or else it would complain, "Property
// 'inputs' does not exist on type 'AbiDefinition'.
// Property 'inputs' does not exist on type
// 'FallbackAbi'.", despite the enclosing if statement.
// tslint:disable:no-unnecessary-type-assertion
parameters = parameters.concat((abi as MethodAbi).inputs);
}
if (abi.hasOwnProperty('outputs')) {
// HACK(feuGeneA): same as described above, except here we
// KNOW that it's a MethodAbi, given the enclosing if
// statement, because that's the only AbiDefinition subtype
// that actually has an outputs field.
parameters = parameters.concat((abi as MethodAbi).outputs);
}
for (const parameter of parameters) {
utils.extractTuples(parameter, tupleBodies, tupleDependencies);
}
}
// build up a list of tuples to declare. the order they're pushed into
// this array is the order they will be declared.
const tuplesToDeclare = [];
// first push the ones that have dependencies
tuplesToDeclare.push(...toposort(tupleDependencies));
// then push any remaining bodies (the ones that DON'T have
// dependencies)
for (const pythonTupleName in tupleBodies) {
if (!tuplesToDeclare.includes(pythonTupleName)) {
tuplesToDeclare.push(pythonTupleName);
}
}
// now iterate over those ordered tuples-to-declare, and prefix the
// corresponding class bodies with their class headers, to form full
// class declarations.
const tupleDeclarations = [];
for (const pythonTupleName of tuplesToDeclare) {
if (tupleBodies[pythonTupleName]) {
tupleDeclarations.push(
`class ${pythonTupleName}(TypedDict):\n """Python representation of a tuple or struct.\n\n Solidity compiler output does not include the names of structs that appear\n in method definitions. A tuple found in an ABI may have been written in\n Solidity as a literal, anonymous tuple, or it may have been written as a\n named \`struct\`:code:, but there is no way to tell from the compiler\n output. This class represents a tuple that appeared in a method\n definition. Its name is derived from a hash of that tuple's field names,\n and every method whose ABI refers to a tuple with that same list of field\n names will have a generated wrapper method that refers to this class.\n\n Any members of type \`bytes\`:code: should be encoded as UTF-8, which can be\n accomplished via \`str.encode("utf_8")\`:code:\n """${
tupleBodies[pythonTupleName]
}`,
);
}
}
// finally, join the class declarations together for the output file
return new Handlebars.SafeString(tupleDeclarations.join('\n\n\n'));
});
Handlebars.registerHelper('docBytesIfNecessary', (abisJSON: string) => {
const abis: AbiDefinition[] = JSON.parse(abisJSON);
// see if any ABIs accept params of type bytes, and if so then emit
// explanatory documentation string.
for (const abi of abis) {
if (abi.hasOwnProperty('inputs')) {
// HACK(feuGeneA): using "as MethodAbi" below, but abi
// could just as well be ConstructorAbi, EventAbi, etc. We
// just need to tell the TypeScript compiler that it's NOT
// FallbackAbi, or else it would complain, "Property
// 'inputs' does not exist on type 'AbiDefinition'.
// Property 'inputs' does not exist on type
// 'FallbackAbi'.", despite the enclosing if statement.
// tslint:disable:no-unnecessary-type-assertion
if ((abi as MethodAbi).inputs) {
for (const input of (abi as MethodAbi).inputs) {
if (input.type === 'bytes') {
return new Handlebars.SafeString(
'\n\n All method parameters of type `bytes`:code: should be encoded as UTF-8,\n which can be accomplished via `str.encode("utf_8")`:code:.\n ',
);
}
}
}
}
}
return '';
});
Handlebars.registerHelper('toPythonClassname', (sourceName: string) => {
let pascalCased = changeCase.pascal(sourceName);
// Retain trailing underscores.
const m = /^.+?(_*)$/.exec(sourceName);
if (m) {
pascalCased = `${pascalCased}${m[1]}`;
}
return new Handlebars.SafeString(pascalCased);
});
Handlebars.registerHelper(
'makeOutputsValue',
/**
* Produces a Python expression representing the return value from a
* Solidity function.
* @param pythonVariable the name of the Python variable holding the value
* to be used to populate the output expression.
* @param abiOutputs the "outputs" object of the function's ABI.
*/
(pythonVariable: string, abiOutputs: DataItem[]) => {
if (abiOutputs.length === 1) {
return new Handlebars.SafeString(solValueToPyValue(pythonVariable, abiOutputs[0]));
} else {
let tupleValue = '(';
for (let i = 0; i < abiOutputs.length; i++) {
tupleValue += `${pythonVariable}[${i}],`;
}
tupleValue += ')';
return new Handlebars.SafeString(tupleValue);
}
},
);
}
function solValueToPyValue(pythonVariable: string, abiItem: DataItem): string {
const pythonTypeName = utils.solTypeToPyType(abiItem);
if (pythonTypeName.match(/List\[.*\]/) !== null) {
return `[${solValueToPyValue('element', {
...abiItem,
type: abiItem.type.replace('[]', ''),
})} for element in ${pythonVariable}]`;
} else {
let pyValue = `${pythonTypeName}(`;
if (abiItem.components) {
let i = 0;
for (const component of abiItem.components) {
pyValue += `${component.name}=${pythonVariable}[${i}],`;
i++;
}
} else {
pyValue += pythonVariable;
}
pyValue += ')';
return pyValue;
}
}

View File

@ -1,24 +0,0 @@
import { ContractAbi, EventAbi, MethodAbi } from 'ethereum-types';
export enum ParamKind {
Input = 'input',
Output = 'output',
}
export enum ContractsBackend {
Web3 = 'web3',
Ethers = 'ethers',
}
export interface Method extends MethodAbi {
singleReturnValue: boolean;
hasReturnValue: boolean;
languageSpecificName: string;
functionSignature: string;
}
export interface ContextData {
contractName: string;
ABI: ContractAbi;
methods: Method[];
events: EventAbi[];
}

View File

@ -1,386 +0,0 @@
import { createHash } from 'crypto';
import * as changeCase from 'change-case';
import * as cliFormat from 'cli-format';
import { AbiType, ConstructorAbi, DataItem, TupleDataItem } from 'ethereum-types';
import * as fs from 'fs';
import * as _ from 'lodash';
import * as path from 'path';
import toSnakeCase = require('to-snake-case');
import { ContractsBackend, ParamKind } from './types';
export const utils = {
solTypeToAssertion(solName: string, solType: string): string {
const trailingArrayRegex = /\[\d*\]$/;
if (solType.match(trailingArrayRegex)) {
const assertion = `assert.isArray('${solName}', ${solName});`;
return assertion;
} else {
const solTypeRegexToTsType = [
{
regex: '^u?int(8|16|32)?$',
assertion: `assert.isNumberOrBigNumber('${solName}', ${solName});`,
},
{ regex: '^string$', assertion: `assert.isString('${solName}', ${solName});` },
{ regex: '^address$', assertion: `assert.isString('${solName}', ${solName});` },
{ regex: '^bool$', assertion: `assert.isBoolean('${solName}', ${solName});` },
{ regex: '^u?int\\d*$', assertion: `assert.isBigNumber('${solName}', ${solName});` },
{ regex: '^bytes\\d*$', assertion: `assert.isString('${solName}', ${solName});` },
];
for (const regexAndTxType of solTypeRegexToTsType) {
const { regex, assertion } = regexAndTxType;
if (solType.match(regex)) {
return assertion;
}
}
const TUPLE_TYPE_REGEX = '^tuple$';
if (solType.match(TUPLE_TYPE_REGEX)) {
// NOTE(fabio): Omit assertions for complex types since this would require taking a type
// definition and generating an instance of that type programmatically and checking it
// against a list of know json-schemas in order to discover the correct schema assertion
// to use. This approach is brittle and error-prone.
const assertion = '';
return assertion;
}
throw new Error(`Unknown Solidity type found: ${solType}`);
}
},
solTypeToTsType(paramKind: ParamKind, backend: ContractsBackend, solType: string, components?: DataItem[]): string {
const trailingArrayRegex = /\[\d*\]$/;
if (solType.match(trailingArrayRegex)) {
const arrayItemSolType = solType.replace(trailingArrayRegex, '');
const arrayItemTsType = utils.solTypeToTsType(paramKind, backend, arrayItemSolType, components);
const arrayTsType =
utils.isUnionType(arrayItemTsType) || utils.isObjectType(arrayItemTsType)
? `Array<${arrayItemTsType}>`
: `${arrayItemTsType}[]`;
return arrayTsType;
} else {
const solTypeRegexToTsType = [
{ regex: '^string$', tsType: 'string' },
{ regex: '^address$', tsType: 'string' },
{ regex: '^bool$', tsType: 'boolean' },
{ regex: '^u?int\\d*$', tsType: 'BigNumber' },
{ regex: '^bytes\\d*$', tsType: 'string' },
];
if (paramKind === ParamKind.Input) {
// web3 and ethers allow to pass those as numbers instead of bignumbers
solTypeRegexToTsType.unshift({
regex: '^u?int(8|16|32)?$',
tsType: 'number|BigNumber',
});
}
if (backend === ContractsBackend.Ethers && paramKind === ParamKind.Output) {
// ethers-contracts automatically converts small BigNumbers to numbers
solTypeRegexToTsType.unshift({
regex: '^u?int(8|16|32|48)?$',
tsType: 'number',
});
}
for (const regexAndTxType of solTypeRegexToTsType) {
const { regex, tsType } = regexAndTxType;
if (solType.match(regex)) {
return tsType;
}
}
const TUPLE_TYPE_REGEX = '^tuple$';
if (solType.match(TUPLE_TYPE_REGEX)) {
const componentsType = _.map(components, component => {
const componentValueType = utils.solTypeToTsType(
paramKind,
backend,
component.type,
component.components,
);
const componentType = `${component.name}: ${componentValueType}`;
return componentType;
});
const tsType = `{${componentsType.join(';')}}`;
return tsType;
}
throw new Error(`Unknown Solidity type found: ${solType}`);
}
},
solTypeToPyType(dataItem: DataItem): string {
const solType = dataItem.type;
const trailingArrayRegex = /\[\d*\]$/;
if (solType.match(trailingArrayRegex)) {
const arrayItemPyType = utils.solTypeToPyType({
...dataItem,
type: dataItem.type.replace(trailingArrayRegex, ''),
});
const arrayPyType = `List[${arrayItemPyType}]`;
return arrayPyType;
} else {
const solTypeRegexToPyType = [
{ regex: '^string$', pyType: 'str' },
{ regex: '^address$', pyType: 'str' },
{ regex: '^bool$', pyType: 'bool' },
{ regex: '^u?int\\d*$', pyType: 'int' },
{ regex: '^bytes\\d*$', pyType: 'Union[bytes, str]' },
];
for (const regexAndTxType of solTypeRegexToPyType) {
const { regex, pyType } = regexAndTxType;
if (solType.match(regex)) {
return pyType;
}
}
const TUPLE_TYPE_REGEX = '^tuple$';
if (solType.match(TUPLE_TYPE_REGEX)) {
return utils.makePythonTupleName(dataItem);
}
throw new Error(`Unknown Solidity type found: ${solType}`);
}
},
isUnionType(tsType: string): boolean {
return tsType === 'number|BigNumber';
},
isObjectType(tsType: string): boolean {
return /^{.*}$/.test(tsType);
},
getPartialNameFromFileName(filename: string): string {
const name = path.parse(filename).name;
return name;
},
getNamedContent(filename: string): { name: string; content: string } {
const name = utils.getPartialNameFromFileName(filename);
try {
const content = fs.readFileSync(filename).toString();
return {
name,
content,
};
} catch (err) {
throw new Error(`Failed to read ${filename}: ${err}`);
}
},
getEmptyConstructor(): ConstructorAbi {
return {
type: AbiType.Constructor,
stateMutability: 'nonpayable',
payable: false,
inputs: [],
};
},
makeOutputFileName(name: string): string {
let fileName = toSnakeCase(name);
// HACK: Snake case doesn't make a lot of sense for abbreviated names but we can't reliably detect abbreviations
// so we special-case the abbreviations we use.
fileName = fileName.replace('z_r_x', 'zrx').replace('e_r_c', 'erc');
return fileName;
},
writeOutputFile(filePath: string, renderedTsCode: string): void {
fs.writeFileSync(filePath, renderedTsCode);
},
isOutputFileUpToDate(outputFile: string, sourceFiles: string[]): boolean {
const sourceFileModTimeMs = sourceFiles.map(file => fs.statSync(file).mtimeMs);
try {
const outFileModTimeMs = fs.statSync(outputFile).mtimeMs;
return sourceFileModTimeMs.find(sourceMs => sourceMs > outFileModTimeMs) === undefined;
} catch (err) {
if (err.code === 'ENOENT') {
return false;
} else {
throw err;
}
}
},
/**
* simply concatenate all of the names of the components, and convert that
* concatenation into PascalCase to conform to Python convention.
*/
makePythonTupleName(tuple: DataItem): string {
if (tuple.internalType !== undefined) {
return tuple.internalType
.replace('struct ', '')
.replace('.', '')
.replace(/\[\]/g, '');
} else {
const tupleComponents = tuple.components;
const lengthOfHashSuffix = 8;
return `Tuple0x${createHash('MD5')
.update(_.map(tupleComponents, component => component.name).join('_'))
.digest()
.toString('hex')
.substring(0, lengthOfHashSuffix)}`;
}
},
/**
* @returns a string that is a Python code snippet that's intended to be
* used as the second parameter to a TypedDict() instantiation; value
* looks like "{ 'python_dict_key': python_type, ... }".
*/
makePythonTupleClassBody(tupleComponents: DataItem[]): string {
let toReturn: string = '';
for (const tupleComponent of tupleComponents) {
toReturn = `${toReturn}\n\n ${tupleComponent.name}: ${utils.solTypeToPyType(tupleComponent)}`;
}
toReturn = `${toReturn}`;
return toReturn;
},
/**
* used to generate Python-parseable identifier names for parameters to
* contract methods.
*/
toPythonIdentifier(input: string): string {
let snakeCased = changeCase.snake(input);
const pythonReservedWords = [
'False',
'None',
'True',
'and',
'as',
'assert',
'break',
'class',
'continue',
'def',
'del',
'elif',
'else',
'except',
'finally',
'for',
'from',
'global',
'if',
'import',
'in',
'is',
'lambda',
'nonlocal',
'not',
'or',
'pass',
'raise',
'return',
'try',
'while',
'with',
'yield',
];
const pythonBuiltins = [
'abs',
'delattr',
'hash',
'memoryview',
'set',
'all',
'dict',
'help',
'min',
'setattr',
'any',
'dir',
'hex',
'next',
'slice',
'ascii',
'divmod',
'id',
'object',
'sorted',
'bin',
'enumerate',
'input',
'oct',
'staticmethod',
'bool',
'eval',
'int',
'open',
'str',
'breakpoint',
'exec',
'isinstance',
'ord',
'sum',
'bytearray',
'filter',
'issubclass',
'pow',
'super',
'bytes',
'float',
'iter',
'print',
'tuple',
'callable',
'format',
'len',
'property',
'type',
'chr',
'frozenset',
'list',
'range',
'vars',
'classmethod',
'getattr',
'locals',
'repr',
'zip',
'compile',
'globals',
'map',
'reversed',
'__import__',
'complex',
'hasattr',
'max',
'round',
];
if (pythonReservedWords.includes(snakeCased) || pythonBuiltins.includes(snakeCased)) {
snakeCased = `_${snakeCased}`;
}
// Retain trailing underscores.
const m = /^.+?(_*)$/.exec(input);
if (m) {
snakeCased = `${snakeCased}${m[1]}`;
}
return snakeCased;
},
/**
* Python docstrings are used to generate documentation, and that
* transformation supports annotation of parameters, return types, etc, via
* re-Structured Text "interpreted text roles". Per the pydocstyle linter,
* such annotations should be line-wrapped at 80 columns, with a hanging
* indent of 4 columns. This function simply returns an accordingly
* wrapped and hanging-indented `role` string.
*/
wrapPythonDocstringRole(docstring: string, indent: number): string {
const columnsPerIndent = 4;
const columnsPerRow = 80;
return cliFormat.wrap(docstring, {
paddingLeft: ' '.repeat(indent),
width: columnsPerRow,
ansi: false,
hangingIndent: ' '.repeat(columnsPerIndent),
});
},
extractTuples(
parameter: DataItem,
tupleBodies: { [pythonTupleName: string]: string }, // output
tupleDependencies: Array<[string, string]>, // output
): void {
if (parameter.type === 'tuple' || parameter.type === 'tuple[]') {
const tupleDataItem = parameter as TupleDataItem; // tslint:disable-line:no-unnecessary-type-assertion
// without the above cast (which tslint complains about), tsc says
// Argument of type 'DataItem[] | undefined' is not assignable to parameter of type 'DataItem[]'.
// Type 'undefined' is not assignable to type 'DataItem[]'
// when the code below tries to access tupleDataItem.components.
const pythonTupleName = utils.makePythonTupleName(tupleDataItem);
tupleBodies[pythonTupleName] = utils.makePythonTupleClassBody(tupleDataItem.components);
for (const component of tupleDataItem.components) {
if (component.type === 'tuple' || component.type === 'tuple[]') {
tupleDependencies.push([
utils.makePythonTupleName(component as TupleDataItem), // tslint:disable-line:no-unnecessary-type-assertion
pythonTupleName,
]);
utils.extractTuples(component, tupleBodies, tupleDependencies);
}
}
}
},
};

View File

@ -1 +0,0 @@
class Account: ...

View File

@ -1,3 +0,0 @@
class LocalAccount:
address: str
...

View File

@ -1 +0,0 @@
class HexBytes: ...

View File

@ -1,67 +0,0 @@
from typing import Any, Callable, Dict, List, Optional, Union
from hexbytes import HexBytes
from eth_account.local import LocalAccount
from web3 import datastructures
from web3.contract import Contract
from web3.providers.base import BaseProvider
class Web3:
class HTTPProvider(BaseProvider):
...
def __init__(self, provider: BaseProvider) -> None: ...
@staticmethod
def sha3(
primitive: Optional[Union[bytes, int, None]] = None,
text: Optional[str] = None,
hexstr: Optional[str] = None
) -> bytes: ...
@staticmethod
def isAddress(address: str) -> bool: ...
class middleware_stack:
@staticmethod
def get(key: str) -> Callable: ...
def inject(
self, middleware_func: object, layer: object
) -> None: ...
...
middleware_onion: middleware_stack
class net:
version: str
...
class Eth:
defaultAccount: str
accounts: List[str]
chainId: int
...
class account:
@staticmethod
def privateKeyToAccount(private_key: str) -> LocalAccount: ...
...
@staticmethod
def getTransactionReceipt(tx_hash: Union[HexBytes, bytes]) -> Any: ...
@staticmethod
def contract(address: str, abi: Dict) -> Contract: ...
...
@staticmethod
def isAddress(address: str) -> bool: ...
...
eth: Eth
...

View File

@ -1,17 +0,0 @@
from typing import Any
class Contract:
def call(self): ...
functions: Any
events: Any
...
class ContractFunction:
def __call__(self, *args, **kwargs):
...
...

View File

@ -1,5 +0,0 @@
class NamedElementOnion:
...
class AttributeDict:
...

View File

@ -1,2 +0,0 @@
class BadFunctionCallOutput(Exception):
...

View File

@ -1,2 +0,0 @@
class BaseProvider:
...

View File

@ -1,133 +0,0 @@
"""Generated wrapper for {{contractName}} Solidity contract."""
# pylint: disable=too-many-arguments
import json
from typing import ( # pylint: disable=unused-import
Any,
List,
Optional,
Tuple,
Union,
)
from eth_utils import to_checksum_address
from mypy_extensions import TypedDict # pylint: disable=unused-import
from hexbytes import HexBytes
from web3 import Web3
from web3.contract import ContractFunction
from web3.datastructures import AttributeDict
from web3.providers.base import BaseProvider
from zero_ex.contract_wrappers.bases import ContractMethod, Validator
from zero_ex.contract_wrappers.tx_params import TxParams
# Try to import a custom validator class definition; if there isn't one,
# declare one that we can instantiate for the default argument to the
# constructor for {{contractName}} below.
try:
# both mypy and pylint complain about what we're doing here, but this
# works just fine, so their messages have been disabled here.
from . import ( # type: ignore # pylint: disable=import-self
{{contractName}}Validator,
)
except ImportError:
class {{contractName}}Validator( # type: ignore
Validator
):
"""No-op input validator."""
try:
from .middleware import MIDDLEWARE # type: ignore
except ImportError:
pass
{{tupleDefinitions ABIString}}
{{#each methods}}
{{> method_class contractName=../contractName}}
{{/each}}
# pylint: disable=too-many-public-methods,too-many-instance-attributes
class {{contractName}}:
"""Wrapper class for {{contractName}} Solidity contract.{{docBytesIfNecessary ABIString}}"""
{{#each methods}}
{{toPythonIdentifier this.languageSpecificName}}: {{toPythonClassname this.languageSpecificName}}Method
"""Constructor-initialized instance of
:class:`{{toPythonClassname this.languageSpecificName}}Method`.
"""
{{/each}}
def __init__(
self,
web3_or_provider: Union[Web3, BaseProvider],
contract_address: str,
validator: {{contractName}}Validator = None,
):
"""Get an instance of wrapper for smart contract.
:param web3_or_provider: Either an instance of `web3.Web3`:code: or
`web3.providers.base.BaseProvider`:code:
:param contract_address: where the contract has been deployed
:param validator: for validation of method inputs.
"""
# pylint: disable=too-many-statements
self.contract_address = contract_address
if not validator:
validator = {{contractName}}Validator(web3_or_provider, contract_address)
web3 = None
if isinstance(web3_or_provider, BaseProvider):
web3 = Web3(web3_or_provider)
elif isinstance(web3_or_provider, Web3):
web3 = web3_or_provider
else:
raise TypeError(
"Expected parameter 'web3_or_provider' to be an instance of either"
+ " Web3 or BaseProvider"
)
# if any middleware was imported, inject it
try:
MIDDLEWARE
except NameError:
pass
else:
try:
for middleware in MIDDLEWARE:
web3.middleware_onion.inject(
middleware['function'], layer=middleware['layer'],
)
except ValueError as value_error:
if value_error.args == ("You can't add the same un-named instance twice",):
pass
self._web3_eth = web3.eth
{{#if methods}}
functions = self._web3_eth.contract(address=to_checksum_address(contract_address), abi={{contractName}}.abi()).functions
{{#each methods}}
self.{{toPythonIdentifier this.languageSpecificName}} = {{toPythonClassname this.languageSpecificName}}Method(web3_or_provider, contract_address, functions.{{this.name}}{{#if this.inputs}}, validator{{/if}})
{{/each}}
{{/if}}
{{#each events}}
{{> event contractName=../contractName}}
{{/each}}
@staticmethod
def abi():
"""Return the ABI to the underlying contract."""
return json.loads(
'{{{ABIString}}}' # noqa: E501 (line-too-long)
)
# pylint: disable=too-many-lines

View File

@ -1,11 +0,0 @@
{{~#if outputs~}}
{{#if outputs.length}}
{{#singleReturnValue}}
{{#returnType outputs.[0]}}{{~/returnType~}}
{{/singleReturnValue}}
{{^singleReturnValue}}
Tuple[{{#each outputs}}{{#returnType this}}{{/returnType}}{{#unless @last}}, {{/unless}}{{/each}}]
{{~/singleReturnValue}}
{{else}}None
{{/if}}
{{else}}None{{/if~}}

View File

@ -1,9 +0,0 @@
def get_{{languageSpecificName}}_event(
self, tx_hash: Union[HexBytes, bytes]
) -> Tuple[AttributeDict]:
"""Get log entry for {{name}} event.
{{makeEventParameterDocstringRole name 8}}
"""
tx_receipt = self._web3_eth.getTransactionReceipt(tx_hash)
return self._web3_eth.contract(address=to_checksum_address(self.contract_address), abi={{contractName}}.abi()).events.{{name}}().processReceipt(tx_receipt)

View File

@ -1,78 +0,0 @@
class {{toPythonClassname this.languageSpecificName}}Method(ContractMethod): # pylint: disable=invalid-name
"""Various interfaces to the {{this.name}} method."""
def __init__(self, web3_or_provider: Union[Web3, BaseProvider], contract_address: str, contract_function: ContractFunction{{#if inputs}}, validator: Validator=None{{/if}}):
"""Persist instance data."""
super().__init__(web3_or_provider, contract_address{{#if inputs}}, validator{{/if}})
self._underlying_method = contract_function
{{#if inputs}}
def validate_and_normalize_inputs(self, {{> typed_params inputs=inputs}}):
"""Validate the inputs to the {{this.name}} method."""
{{#each this.inputs}}
self.validator.assert_valid(
method_name='{{../name}}',
parameter_name='{{name}}',
argument_value={{toPythonIdentifier name}},
)
{{#if (equal type 'address')}}
{{toPythonIdentifier this.name}} = self.validate_and_checksum_address({{toPythonIdentifier this.name}})
{{else if (equal type 'uint256')}}
# safeguard against fractional inputs
{{toPythonIdentifier this.name}} = int({{toPythonIdentifier this.name}})
{{/if}}
{{/each}}
return ({{> params }})
{{/if}}
def call(self, {{#if inputs}}{{> typed_params inputs=inputs}}, {{/if}}tx_params: Optional[TxParams] = None) -> {{> call_return_type outputs=outputs type='call'~}}:
"""Execute underlying contract method via eth_call.
{{sanitizeDevdocDetails this.name this.devdoc.details 8}}{{~#if this.devdoc.params~}}{{#each this.devdoc.params}}
{{makeParameterDocstringRole @key this 8}}{{/each}}{{/if}}
:param tx_params: transaction parameters
{{#if this.constant~}}
{{#if this.devdoc.return}}
{{makeReturnDocstringRole this.devdoc.return 8}}{{/if}}
{{else}}
:returns: the return value of the underlying method.
{{/if}}
"""
{{#if inputs}}
({{> params }}) = self.validate_and_normalize_inputs({{> params}})
{{/if}}
tx_params = super().normalize_tx_params(tx_params)
{{#hasReturnValue}}returned = {{/hasReturnValue}}self._underlying_method({{> params}}).call(tx_params.as_dict())
{{#hasReturnValue}}
return {{makeOutputsValue 'returned' outputs}}
{{/hasReturnValue}}
{{^if this.constant}}
def send_transaction(self, {{#if inputs}}{{> typed_params inputs=inputs}}, {{/if}}tx_params: Optional[TxParams] = None) -> Union[HexBytes, bytes]:
"""Execute underlying contract method via eth_sendTransaction.
{{sanitizeDevdocDetails this.name this.devdoc.details 8}}{{~#if this.devdoc.params~}}{{#each this.devdoc.params}}
{{makeParameterDocstringRole @key this 8}}{{/each}}{{/if}}
:param tx_params: transaction parameters
"""
{{#if inputs}}
({{> params }}) = self.validate_and_normalize_inputs({{> params}})
{{/if}}
tx_params = super().normalize_tx_params(tx_params)
return self._underlying_method({{> params}}).transact(tx_params.as_dict())
def build_transaction(self, {{#if inputs}}{{> typed_params inputs=inputs}}, {{/if}}tx_params: Optional[TxParams] = None) -> dict:
"""Construct calldata to be used as input to the method."""
{{#if inputs}}
({{> params }}) = self.validate_and_normalize_inputs({{> params}})
{{/if}}
tx_params = super().normalize_tx_params(tx_params)
return self._underlying_method({{> params}}).buildTransaction(tx_params.as_dict())
{{/if}}
def estimate_gas(self, {{#if inputs}}{{> typed_params inputs=inputs}}, {{/if}}tx_params: Optional[TxParams] = None) -> int:
"""Estimate gas consumption of method call."""
{{#if inputs}}
({{> params }}) = self.validate_and_normalize_inputs({{> params}})
{{/if}}
tx_params = super().normalize_tx_params(tx_params)
return self._underlying_method({{> params}}).estimateGas(tx_params.as_dict())

View File

@ -1,3 +0,0 @@
{{#each inputs}}
{{toPythonIdentifier name}}{{#if @last}}{{else}}, {{/if~}}
{{/each~}}

View File

@ -1,14 +0,0 @@
{{~#if outputs~}}
{{^if this.constant}}
Union[
{{~/if~}}
{{#if outputs.length}}
{{#singleReturnValue}}
{{#returnType outputs.[0]}}{{~/returnType~}}
{{/singleReturnValue}}
{{^singleReturnValue}}
Tuple[{{#each outputs}}{{#returnType this}}{{/returnType}}{{#unless @last}}, {{/unless}}{{/each}}]
{{~/singleReturnValue}}
{{else}}None
{{/if}}{{^if this.constant}}, Union[HexBytes, bytes]]{{/if~}}
{{else}}{{#if this.constant}}None{{else}}Union[None, Union[HexBytes, bytes]]{{/if}}{{/if~}}

View File

@ -1,3 +0,0 @@
{{#each inputs}}
{{toPythonIdentifier name}}: {{#parameterType this}}{{/parameterType}}{{^if @last}}, {{/if~}}
{{/each~}}

View File

@ -1,416 +0,0 @@
// tslint:disable:no-consecutive-blank-lines ordered-imports align trailing-comma enum-naming
// tslint:disable:whitespace no-unbound-method no-trailing-whitespace
// tslint:disable:no-unused-variable
import {
AwaitTransactionSuccessOpts,
ContractFunctionObj,
ContractTxFunctionObj,
SendTransactionOpts,
BaseContract,
{{#if events~}}SubscriptionManager,{{/if~}}
PromiseWithTransactionHash,
methodAbiToFunctionSignature,
linkLibrariesInBytecode,
} from '@0x/base-contract';
import { schemas } from '@0x/json-schemas';
import {
BlockParam,
BlockParamLiteral,
BlockRange,
CallData,
ContractAbi,
ContractArtifact,
DecodedLogArgs,{{#if events}}
LogWithDecodedArgs,{{/if}}
MethodAbi,
TransactionReceiptWithDecodedLogs,
TxData,
TxDataPayable,
SupportedProvider,
} from 'ethereum-types';
import { BigNumber, classUtils, hexUtils, logUtils, providerUtils } from '@0x/utils';
import { EventCallback, IndexedFilterValues, SimpleContractArtifact } from '@0x/types';
import { Web3Wrapper } from '@0x/web3-wrapper';
import { assert } from '@0x/assert';
import * as ethers from 'ethers';
// tslint:enable:no-unused-variable
{{#if events}}
export type {{contractName}}EventArgs =
{{#each events}}
| {{@root.contractName}}{{name}}EventArgs{{#if @last}};{{/if}}
{{/each}}
export enum {{contractName}}Events {
{{#each events}}
{{name}} = '{{name}}',
{{/each}}
}
{{#each events}}
{{> event}}
{{/each}}
{{/if}}
/* istanbul ignore next */
// tslint:disable:array-type
// tslint:disable:no-parameter-reassignment
// tslint:disable-next-line:class-name
export class {{contractName}}Contract extends BaseContract {
/**
* @ignore
*/
{{#ifEquals this.deployedBytecode undefined~}}
public static deployedBytecode: string | undefined;
{{else~}}
public static deployedBytecode = '{{this.deployedBytecode}}';
{{/ifEquals~}}
public static contractName = '{{contractName}}';
private readonly _methodABIIndex: { [name: string]: number } = {};
{{#if events~}}
private readonly _subscriptionManager: SubscriptionManager<{{contractName}}EventArgs, {{contractName}}Events>;
{{/if~}}
public static async deployFrom0xArtifactAsync(
artifact: ContractArtifact | SimpleContractArtifact,
supportedProvider: SupportedProvider,
txDefaults: Partial<TxData>,
logDecodeDependencies: { [contractName: string]: (ContractArtifact | SimpleContractArtifact) },
{{> typed_params inputs=ctor.inputs}}
): Promise<{{contractName}}Contract> {
assert.doesConformToSchema('txDefaults', txDefaults, schemas.txDataSchema, [
schemas.addressSchema,
schemas.numberSchema,
schemas.jsNumber,
]);
if (artifact.compilerOutput === undefined) {
throw new Error('Compiler output not found in the artifact file');
}
const provider = providerUtils.standardizeOrThrow(supportedProvider);
const bytecode = artifact.compilerOutput.evm.bytecode.object;
const abi = artifact.compilerOutput.abi;
const logDecodeDependenciesAbiOnly: { [contractName: string]: ContractAbi } = {};
if (Object.keys(logDecodeDependencies) !== undefined) {
for (const key of Object.keys(logDecodeDependencies)) {
logDecodeDependenciesAbiOnly[key] = logDecodeDependencies[key].compilerOutput.abi;
}
}
return {{contractName}}Contract.deployAsync(bytecode, abi, provider, txDefaults, logDecodeDependenciesAbiOnly, {{> params inputs=ctor.inputs}});
}
public static async deployWithLibrariesFrom0xArtifactAsync(
artifact: ContractArtifact,
libraryArtifacts: { [libraryName: string]: ContractArtifact },
supportedProvider: SupportedProvider,
txDefaults: Partial<TxData>,
logDecodeDependencies: { [contractName: string]: (ContractArtifact | SimpleContractArtifact) },
{{> typed_params inputs=ctor.inputs}}
): Promise<{{contractName}}Contract> {
assert.doesConformToSchema('txDefaults', txDefaults, schemas.txDataSchema, [
schemas.addressSchema,
schemas.numberSchema,
schemas.jsNumber,
]);
if (artifact.compilerOutput === undefined) {
throw new Error('Compiler output not found in the artifact file');
}
const provider = providerUtils.standardizeOrThrow(supportedProvider);
const abi = artifact.compilerOutput.abi;
const logDecodeDependenciesAbiOnly: { [contractName: string]: ContractAbi } = {};
if (Object.keys(logDecodeDependencies) !== undefined) {
for (const key of Object.keys(logDecodeDependencies)) {
logDecodeDependenciesAbiOnly[key] = logDecodeDependencies[key].compilerOutput.abi;
}
}
const libraryAddresses = await {{contractName}}Contract._deployLibrariesAsync(
artifact,
libraryArtifacts,
new Web3Wrapper(provider),
txDefaults
);
const bytecode = linkLibrariesInBytecode(
artifact,
libraryAddresses,
);
return {{contractName}}Contract.deployAsync(bytecode, abi, provider, txDefaults, logDecodeDependenciesAbiOnly, {{> params inputs=ctor.inputs}});
}
public static async deployAsync(
bytecode: string,
abi: ContractAbi,
supportedProvider: SupportedProvider,
txDefaults: Partial<TxData>,
logDecodeDependencies: { [contractName: string]: ContractAbi },
{{> typed_params inputs=ctor.inputs}}
): Promise<{{contractName}}Contract> {
assert.isHexString('bytecode', bytecode);
assert.doesConformToSchema('txDefaults', txDefaults, schemas.txDataSchema, [
schemas.addressSchema,
schemas.numberSchema,
schemas.jsNumber,
]);
const provider = providerUtils.standardizeOrThrow(supportedProvider);
const constructorAbi = BaseContract._lookupConstructorAbi(abi);
[{{> params inputs=ctor.inputs}}] = BaseContract._formatABIDataItemList(
constructorAbi.inputs,
[{{> params inputs=ctor.inputs}}],
BaseContract._bigNumberToString,
);
const iface = new ethers.utils.Interface(abi);
const deployInfo = iface.deployFunction;
const txData = deployInfo.encode(bytecode, [{{> params inputs=ctor.inputs}}]);
const web3Wrapper = new Web3Wrapper(provider);
const txDataWithDefaults = await BaseContract._applyDefaultsToContractTxDataAsync(
{
data: txData,
...txDefaults,
},
web3Wrapper.estimateGasAsync.bind(web3Wrapper),
);
const txHash = await web3Wrapper.sendTransactionAsync(txDataWithDefaults);
logUtils.log(`transactionHash: ${txHash}`);
const txReceipt = await web3Wrapper.awaitTransactionSuccessAsync(txHash);
logUtils.log(`{{contractName}} successfully deployed at ${txReceipt.contractAddress}`);
const contractInstance = new {{contractName}}Contract(txReceipt.contractAddress as string, provider, txDefaults, logDecodeDependencies);
contractInstance.constructorArgs = [{{> params inputs=ctor.inputs}}];
return contractInstance;
}
/**
* @returns The contract ABI
*/
public static ABI(): ContractAbi {
const abi = [
{{#each ABI}}
{ {{#if (isDefined this.constant)}}
constant: {{constant}},{{/if}}{{#if (isDefined this.anonymous)}}
anonymous: {{anonymous}},{{/if}}
inputs: [
{{#each inputs}}
{{> abi_type this}}
{{/each}}
],{{#this.name}}
name: '{{{this}}}',{{/this.name}}
outputs: [
{{#each outputs}}
{{> abi_type this}}
{{/each}}
],{{#if (isDefined this.payable)}}
payable: {{payable}},{{/if}}{{#this.stateMutability}}
stateMutability: '{{this}}',{{/this.stateMutability}}
type: '{{type}}',
},
{{/each}}
] as ContractAbi;
return abi;
}
protected static async _deployLibrariesAsync(
artifact: ContractArtifact,
libraryArtifacts: { [libraryName: string]: ContractArtifact },
web3Wrapper: Web3Wrapper,
txDefaults: Partial<TxData>,
libraryAddresses: { [libraryName: string]: string } = {},
): Promise<{ [libraryName: string]: string }> {
const links = artifact.compilerOutput.evm.bytecode.linkReferences;
// Go through all linked libraries, recursively deploying them if necessary.
for (const link of Object.values(links)) {
for (const libraryName of Object.keys(link)) {
if (!libraryAddresses[libraryName]) {
// Library not yet deployed.
const libraryArtifact = libraryArtifacts[libraryName];
if (!libraryArtifact) {
throw new Error(`Missing artifact for linked library "${libraryName}"`);
}
// Deploy any dependent libraries used by this library.
await {{contractName}}Contract._deployLibrariesAsync(
libraryArtifact,
libraryArtifacts,
web3Wrapper,
txDefaults,
libraryAddresses,
);
// Deploy this library.
const linkedLibraryBytecode = linkLibrariesInBytecode(
libraryArtifact,
libraryAddresses,
);
const txDataWithDefaults = await BaseContract._applyDefaultsToContractTxDataAsync(
{
data: linkedLibraryBytecode,
...txDefaults,
},
web3Wrapper.estimateGasAsync.bind(web3Wrapper),
);
const txHash = await web3Wrapper.sendTransactionAsync(txDataWithDefaults);
logUtils.log(`transactionHash: ${txHash}`);
const { contractAddress } = await web3Wrapper.awaitTransactionSuccessAsync(txHash);
logUtils.log(`${libraryArtifact.contractName} successfully deployed at ${contractAddress}`);
libraryAddresses[libraryArtifact.contractName] = contractAddress as string;
}
}
}
return libraryAddresses;
}
public getFunctionSignature(methodName: string): string {
const index = this._methodABIIndex[methodName];
const methodAbi = {{contractName}}Contract.ABI()[index] as MethodAbi; // tslint:disable-line:no-unnecessary-type-assertion
const functionSignature = methodAbiToFunctionSignature(methodAbi);
return functionSignature;
}
public getABIDecodedTransactionData<T>(methodName: string, callData: string): T {
const functionSignature = this.getFunctionSignature(methodName);
const self = (this as any) as {{contractName}}Contract;
const abiEncoder = self._lookupAbiEncoder(functionSignature);
const abiDecodedCallData = abiEncoder.strictDecode<T>(callData);
return abiDecodedCallData;
}
public getABIDecodedReturnData<T>(methodName: string, callData: string): T {
const functionSignature = this.getFunctionSignature(methodName);
const self = (this as any) as {{contractName}}Contract;
const abiEncoder = self._lookupAbiEncoder(functionSignature);
const abiDecodedCallData = abiEncoder.strictDecodeReturnValue<T>(callData);
return abiDecodedCallData;
}
public getSelector(methodName: string): string {
const functionSignature = this.getFunctionSignature(methodName);
const self = (this as any) as {{contractName}}Contract;
const abiEncoder = self._lookupAbiEncoder(functionSignature);
return abiEncoder.getSelector();
}
{{#each methods}}
{{#if this.devdoc.details}}
/**
* {{formatDocstringForMethodTs this.devdoc.details}}
{{> params_docstring inputs=inputs docstrings=devdoc.params}}
{{#if devdoc.return}}
* @returns {{devdoc.return}}
{{/if}}
*/
{{/if}}
public {{languageSpecificName}}(
{{> typed_params inputs=this.inputs}}
): Contract{{^this.constant}}Tx{{/this.constant}}FunctionObj<{{> return_type outputs=outputs ~}}> {
const self = this as any as {{../contractName}}Contract;
{{#each inputs}}
{{#assertionType name type}}{{/assertionType}}
{{/each}}
const functionSignature = '{{this.functionSignature}}';
return {
{{^this.constant}}
{{> method_tx}}
{{/this.constant}}
{{> method_call stateMutability=this.stateMutability}}
}
};
{{/each}}
{{#if events}}
/**
* Subscribe to an event type emitted by the {{contractName}} contract.
* @param eventName The {{contractName}} contract event you would like to subscribe to.
* @param indexFilterValues An object where the keys are indexed args returned by the event and
* the value is the value you are interested in. E.g `{maker: aUserAddressHex}`
* @param callback Callback that gets called when a log is added/removed
* @param isVerbose Enable verbose subscription warnings (e.g recoverable network issues encountered)
* @return Subscription token used later to unsubscribe
*/
public subscribe<ArgsType extends {{contractName}}EventArgs>(
eventName: {{contractName}}Events,
indexFilterValues: IndexedFilterValues,
callback: EventCallback<ArgsType>,
isVerbose: boolean = false,
blockPollingIntervalMs?: number,
): string {
assert.doesBelongToStringEnum('eventName', eventName, {{contractName}}Events);
assert.doesConformToSchema('indexFilterValues', indexFilterValues, schemas.indexFilterValuesSchema);
assert.isFunction('callback', callback);
const subscriptionToken = this._subscriptionManager.subscribe<ArgsType>(
this.address,
eventName,
indexFilterValues,
{{contractName}}Contract.ABI(),
callback,
isVerbose,
blockPollingIntervalMs,
);
return subscriptionToken;
}
/**
* Cancel a subscription
* @param subscriptionToken Subscription token returned by `subscribe()`
*/
public unsubscribe(subscriptionToken: string): void {
this._subscriptionManager.unsubscribe(subscriptionToken);
}
/**
* Cancels all existing subscriptions
*/
public unsubscribeAll(): void {
this._subscriptionManager.unsubscribeAll();
}
/**
* Gets historical logs without creating a subscription
* @param eventName The {{contractName}} contract event you would like to subscribe to.
* @param blockRange Block range to get logs from.
* @param indexFilterValues An object where the keys are indexed args returned by the event and
* the value is the value you are interested in. E.g `{_from: aUserAddressHex}`
* @return Array of logs that match the parameters
*/
public async getLogsAsync<ArgsType extends {{contractName}}EventArgs>(
eventName: {{contractName}}Events,
blockRange: BlockRange,
indexFilterValues: IndexedFilterValues,
): Promise<Array<LogWithDecodedArgs<ArgsType>>> {
assert.doesBelongToStringEnum('eventName', eventName, {{contractName}}Events);
assert.doesConformToSchema('blockRange', blockRange, schemas.blockRangeSchema);
assert.doesConformToSchema('indexFilterValues', indexFilterValues, schemas.indexFilterValuesSchema);
const logs = await this._subscriptionManager.getLogsAsync<ArgsType>(
this.address,
eventName,
blockRange,
indexFilterValues,
{{contractName}}Contract.ABI(),
);
return logs;
}{{/if}}
constructor(
address: string,
supportedProvider: SupportedProvider,
txDefaults?: Partial<TxData>,
logDecodeDependencies?: { [contractName: string]: ContractAbi },
deployedBytecode: string | undefined = {{contractName}}Contract.deployedBytecode,
) {
super('{{contractName}}', {{contractName}}Contract.ABI(), address, supportedProvider, txDefaults, logDecodeDependencies, deployedBytecode);
classUtils.bindAll(this, ['_abiEncoderByFunctionSignature', 'address', '_web3Wrapper']);
{{#if events~}}
this._subscriptionManager = new SubscriptionManager<{{contractName}}EventArgs, {{contractName}}Events>(
{{contractName}}Contract.ABI(),
this._web3Wrapper,
);
{{/if~}}
{{contractName}}Contract.ABI().forEach((item, index) => {
if (item.type === 'function') {
const methodAbi = item as MethodAbi;
this._methodABIIndex[methodAbi.name] = index;
}
});
}
}
// tslint:disable:max-file-line-count
// tslint:enable:no-unbound-method no-parameter-reassignment no-consecutive-blank-lines ordered-imports align
// tslint:enable:trailing-comma whitespace no-trailing-whitespace

View File

@ -1,10 +0,0 @@
{
name: '{{name}}',
type: '{{type}}',{{#if (isDefined indexed)}}
indexed: {{indexed}},{{/if}}{{#if components}}
components: [
{{#each components}}
{{> abi_type this}}
{{/each}}
]{{/if}}
},

View File

@ -1,5 +0,0 @@
export interface {{@root.contractName}}{{name}}EventArgs extends DecodedLogArgs {
{{#each inputs}}
{{name}}: {{#returnType type components}}{{/returnType}};
{{/each}}
}

View File

@ -1,22 +0,0 @@
async callAsync(
callData: Partial<CallData> = {},
defaultBlock?: BlockParam,
): Promise<{{> return_type outputs=outputs}}> {
BaseContract._assertCallParams(callData, defaultBlock);
{{#ifEquals this.stateMutability "pure" }}
let rawCallResult;
if (self._deployedBytecodeIfExists) {
rawCallResult = await self._evmExecAsync(this.getABIEncodedTransactionData());
} else {
rawCallResult = await self._performCallAsync({ data: this.getABIEncodedTransactionData(), ...callData }, defaultBlock);
}
{{else}}
const rawCallResult = await self._performCallAsync({ data: this.getABIEncodedTransactionData(), ...callData }, defaultBlock);
{{/ifEquals}}
const abiEncoder = self._lookupAbiEncoder(functionSignature);
BaseContract._throwIfUnexpectedEmptyCallResult(rawCallResult, abiEncoder);
return abiEncoder.strictDecodeReturnValue<{{> return_type outputs=outputs}}>(rawCallResult);
},
getABIEncodedTransactionData(): string {
return self._strictEncodeArguments(functionSignature, [{{> normalized_params inputs=inputs}}]);
},

View File

@ -1,27 +0,0 @@
async sendTransactionAsync(
txData?: Partial<TxData> | undefined,
opts: SendTransactionOpts = { shouldValidate: true },
): Promise<string> {
const txDataWithDefaults = await self._applyDefaultsToTxDataAsync(
{ data: this.getABIEncodedTransactionData(), ...txData },
this.estimateGasAsync.bind(this),
);
if (opts.shouldValidate !== false) {
await this.callAsync(txDataWithDefaults);
}
return self._web3Wrapper.sendTransactionAsync(txDataWithDefaults);
},
awaitTransactionSuccessAsync(
txData?: Partial<TxData>,
opts: AwaitTransactionSuccessOpts = { shouldValidate: true },
): PromiseWithTransactionHash<TransactionReceiptWithDecodedLogs> {
return self._promiseWithTransactionHash(this.sendTransactionAsync(txData, opts), opts);
},
async estimateGasAsync(
txData?: Partial<TxData> | undefined,
): Promise<number> {
const txDataWithDefaults = await self._applyDefaultsToTxDataAsync(
{ data: this.getABIEncodedTransactionData(), ...txData }
);
return self._web3Wrapper.estimateGasAsync(txDataWithDefaults);
},

View File

@ -1,3 +0,0 @@
{{#each inputs}}
{{name}}{{#ifEquals 'address' type}}.toLowerCase(){{/ifEquals}}{{#if @last}}{{else}},{{/if}}
{{/each}}

View File

@ -1,3 +0,0 @@
{{#each inputs}}
{{name}}{{#if @last}}{{else}},{{/if}}
{{/each}}

View File

@ -1,5 +0,0 @@
{{#each inputs}}
{{#if (getDocstringForParamTs name ../docstrings)}}
{{formatDocstringForParamTs name (getDocstringForParamTs name ../docstrings)}}
{{/if}}
{{/each}}

View File

@ -1,10 +0,0 @@
{{#if outputs.length}}
{{#singleReturnValue}}
{{#returnType outputs.0.type outputs.0.components}}{{/returnType}}
{{/singleReturnValue}}
{{^singleReturnValue}}
[{{#each outputs}}{{#returnType type components}}{{/returnType}}{{#unless @last}}, {{/unless}}{{/each}}]
{{/singleReturnValue}}
{{else}}
void
{{/if}}

View File

@ -1,3 +0,0 @@
{{#each inputs}}
{{name}}: {{#parameterType type components}}{{/parameterType}},
{{/each}}

File diff suppressed because one or more lines are too long

View File

@ -1,64 +0,0 @@
{
"schemaVersion": "2.0.0",
"contractName": "LibDummy",
"compilerOutput": {
"abi": [],
"devdoc": {
"methods": {}
},
"evm": {
"bytecode": {
"linkReferences": {},
"object": "0x60556023600b82828239805160001a607314601657fe5b30600052607381538281f3fe73000000000000000000000000000000000000000030146080604052600080fdfea265627a7a72315820725ed7971b4c6a8dad5ee5e2dfb2083612f69a239b2ad69690a85c8e21d5f23864736f6c634300050c0032",
"opcodes": "PUSH1 0x55 PUSH1 0x23 PUSH1 0xB DUP3 DUP3 DUP3 CODECOPY DUP1 MLOAD PUSH1 0x0 BYTE PUSH1 0x73 EQ PUSH1 0x16 JUMPI INVALID JUMPDEST ADDRESS PUSH1 0x0 MSTORE PUSH1 0x73 DUP2 MSTORE8 DUP3 DUP2 RETURN INVALID PUSH20 0x0 ADDRESS EQ PUSH1 0x80 PUSH1 0x40 MSTORE PUSH1 0x0 DUP1 REVERT INVALID LOG2 PUSH6 0x627A7A723158 KECCAK256 PUSH19 0x5ED7971B4C6A8DAD5EE5E2DFB2083612F69A23 SWAP12 0x2a 0xd6 SWAP7 SWAP1 0xa8 0x5c DUP15 0x21 0xd5 CALLCODE CODESIZE PUSH5 0x736F6C6343 STOP SDIV 0xc STOP ORIGIN ",
"sourceMap": "606:385:1:-;;132:2:-1;166:7;155:9;146:7;137:37;255:7;249:14;246:1;241:23;235:4;232:33;222:2;;269:9;222:2;293:9;290:1;283:20;323:4;314:7;306:22;347:7;338;331:24"
},
"deployedBytecode": {
"linkReferences": {},
"object": "0x73000000000000000000000000000000000000000030146080604052600080fdfea265627a7a72315820725ed7971b4c6a8dad5ee5e2dfb2083612f69a239b2ad69690a85c8e21d5f23864736f6c634300050c0032",
"opcodes": "PUSH20 0x0 ADDRESS EQ PUSH1 0x80 PUSH1 0x40 MSTORE PUSH1 0x0 DUP1 REVERT INVALID LOG2 PUSH6 0x627A7A723158 KECCAK256 PUSH19 0x5ED7971B4C6A8DAD5EE5E2DFB2083612F69A23 SWAP12 0x2a 0xd6 SWAP7 SWAP1 0xa8 0x5c DUP15 0x21 0xd5 CALLCODE CODESIZE PUSH5 0x736F6C6343 STOP SDIV 0xc STOP ORIGIN ",
"sourceMap": "606:385:1:-;;;;;;;;"
}
}
},
"sources": {
"LibDummy.sol": {
"id": 1
}
},
"sourceCodes": {
"LibDummy.sol": "/*\n\n Copyright 2019 ZeroEx Intl.\n\n Licensed under the Apache License, Version 2.0 (the \"License\");\n you may not use this file except in compliance with the License.\n You may obtain a copy of the License at\n\n http://www.apache.org/licenses/LICENSE-2.0\n\n Unless required by applicable law or agreed to in writing, software\n distributed under the License is distributed on an \"AS IS\" BASIS,\n WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n See the License for the specific language governing permissions and\n limitations under the License.\n\n*/\n\npragma solidity ^0.5.5;\n\n\nlibrary LibDummy {\n\n using LibDummy for uint256;\n uint256 constant internal SOME_CONSTANT = 1234;\n\n function addOne (uint256 x)\n internal\n pure\n returns (uint256 sum)\n {\n return x + 1;\n }\n\n function addConstant (uint256 x)\n internal\n pure\n returns (uint256 someConstant)\n {\n return x + SOME_CONSTANT;\n }\n}\n"
},
"sourceTreeHashHex": "0xd7314c6b96d3195f1d6823802c5a01b0090fe630f4908495ba19d9c298b3ded1",
"compiler": {
"name": "solc",
"version": "soljson-v0.5.12+commit.7709ece9.js",
"settings": {
"optimizer": {
"enabled": true,
"runs": 1000000,
"details": {
"yul": true,
"deduplicate": true,
"cse": true,
"constantOptimizer": true
}
},
"outputSelection": {
"*": {
"*": [
"abi",
"evm.bytecode.object",
"evm.bytecode.sourceMap",
"evm.deployedBytecode.object",
"evm.deployedBytecode.sourceMap",
"devdoc"
]
}
},
"evmVersion": "constantinople",
"remappings": []
}
},
"chains": {}
}

View File

@ -1,111 +0,0 @@
{
"schemaVersion": "2.0.0",
"contractName": "TestLibDummy",
"compilerOutput": {
"abi": [
{
"constant": true,
"inputs": [
{
"internalType": "uint256",
"name": "x",
"type": "uint256"
}
],
"name": "publicAddConstant",
"outputs": [
{
"internalType": "uint256",
"name": "result",
"type": "uint256"
}
],
"payable": false,
"stateMutability": "pure",
"type": "function"
},
{
"constant": true,
"inputs": [
{
"internalType": "uint256",
"name": "x",
"type": "uint256"
}
],
"name": "publicAddOne",
"outputs": [
{
"internalType": "uint256",
"name": "result",
"type": "uint256"
}
],
"payable": false,
"stateMutability": "pure",
"type": "function"
}
],
"devdoc": {
"methods": {}
},
"evm": {
"bytecode": {
"linkReferences": {},
"object": "0x608060405234801561001057600080fd5b5060d78061001f6000396000f3fe6080604052348015600f57600080fd5b506004361060325760003560e01c806322935e921460375780632b82fdf0146063575b600080fd5b605160048036036020811015604b57600080fd5b5035607d565b60408051918252519081900360200190f35b605160048036036020811015607757600080fd5b5035608c565b60006086826095565b92915050565b6000608682609c565b6104d20190565b6001019056fea265627a7a72315820863e53f0da474a1275d583d88852313fe053941e79bddd5279abd812b31e020c64736f6c634300050c0032",
"opcodes": "PUSH1 0x80 PUSH1 0x40 MSTORE CALLVALUE DUP1 ISZERO PUSH2 0x10 JUMPI PUSH1 0x0 DUP1 REVERT JUMPDEST POP PUSH1 0xD7 DUP1 PUSH2 0x1F PUSH1 0x0 CODECOPY PUSH1 0x0 RETURN INVALID PUSH1 0x80 PUSH1 0x40 MSTORE CALLVALUE DUP1 ISZERO PUSH1 0xF JUMPI PUSH1 0x0 DUP1 REVERT JUMPDEST POP PUSH1 0x4 CALLDATASIZE LT PUSH1 0x32 JUMPI PUSH1 0x0 CALLDATALOAD PUSH1 0xE0 SHR DUP1 PUSH4 0x22935E92 EQ PUSH1 0x37 JUMPI DUP1 PUSH4 0x2B82FDF0 EQ PUSH1 0x63 JUMPI JUMPDEST PUSH1 0x0 DUP1 REVERT JUMPDEST PUSH1 0x51 PUSH1 0x4 DUP1 CALLDATASIZE SUB PUSH1 0x20 DUP2 LT ISZERO PUSH1 0x4B JUMPI PUSH1 0x0 DUP1 REVERT JUMPDEST POP CALLDATALOAD PUSH1 0x7D JUMP JUMPDEST PUSH1 0x40 DUP1 MLOAD SWAP2 DUP3 MSTORE MLOAD SWAP1 DUP2 SWAP1 SUB PUSH1 0x20 ADD SWAP1 RETURN JUMPDEST PUSH1 0x51 PUSH1 0x4 DUP1 CALLDATASIZE SUB PUSH1 0x20 DUP2 LT ISZERO PUSH1 0x77 JUMPI PUSH1 0x0 DUP1 REVERT JUMPDEST POP CALLDATALOAD PUSH1 0x8C JUMP JUMPDEST PUSH1 0x0 PUSH1 0x86 DUP3 PUSH1 0x95 JUMP JUMPDEST SWAP3 SWAP2 POP POP JUMP JUMPDEST PUSH1 0x0 PUSH1 0x86 DUP3 PUSH1 0x9C JUMP JUMPDEST PUSH2 0x4D2 ADD SWAP1 JUMP JUMPDEST PUSH1 0x1 ADD SWAP1 JUMP INVALID LOG2 PUSH6 0x627A7A723158 KECCAK256 DUP7 RETURNDATACOPY MSTORE8 CREATE 0xda SELFBALANCE 0x4a SLT PUSH22 0xD583D88852313FE053941E79BDDD5279ABD812B31E02 0xc PUSH5 0x736F6C6343 STOP SDIV 0xc STOP ORIGIN ",
"sourceMap": "632:346:2:-;;;;8:9:-1;5:2;;;30:1;27;20:12;5:2;632:346:2;;;;;;;"
},
"deployedBytecode": {
"linkReferences": {},
"object": "0x6080604052348015600f57600080fd5b506004361060325760003560e01c806322935e921460375780632b82fdf0146063575b600080fd5b605160048036036020811015604b57600080fd5b5035607d565b60408051918252519081900360200190f35b605160048036036020811015607757600080fd5b5035608c565b60006086826095565b92915050565b6000608682609c565b6104d20190565b6001019056fea265627a7a72315820863e53f0da474a1275d583d88852313fe053941e79bddd5279abd812b31e020c64736f6c634300050c0032",
"opcodes": "PUSH1 0x80 PUSH1 0x40 MSTORE CALLVALUE DUP1 ISZERO PUSH1 0xF JUMPI PUSH1 0x0 DUP1 REVERT JUMPDEST POP PUSH1 0x4 CALLDATASIZE LT PUSH1 0x32 JUMPI PUSH1 0x0 CALLDATALOAD PUSH1 0xE0 SHR DUP1 PUSH4 0x22935E92 EQ PUSH1 0x37 JUMPI DUP1 PUSH4 0x2B82FDF0 EQ PUSH1 0x63 JUMPI JUMPDEST PUSH1 0x0 DUP1 REVERT JUMPDEST PUSH1 0x51 PUSH1 0x4 DUP1 CALLDATASIZE SUB PUSH1 0x20 DUP2 LT ISZERO PUSH1 0x4B JUMPI PUSH1 0x0 DUP1 REVERT JUMPDEST POP CALLDATALOAD PUSH1 0x7D JUMP JUMPDEST PUSH1 0x40 DUP1 MLOAD SWAP2 DUP3 MSTORE MLOAD SWAP1 DUP2 SWAP1 SUB PUSH1 0x20 ADD SWAP1 RETURN JUMPDEST PUSH1 0x51 PUSH1 0x4 DUP1 CALLDATASIZE SUB PUSH1 0x20 DUP2 LT ISZERO PUSH1 0x77 JUMPI PUSH1 0x0 DUP1 REVERT JUMPDEST POP CALLDATALOAD PUSH1 0x8C JUMP JUMPDEST PUSH1 0x0 PUSH1 0x86 DUP3 PUSH1 0x95 JUMP JUMPDEST SWAP3 SWAP2 POP POP JUMP JUMPDEST PUSH1 0x0 PUSH1 0x86 DUP3 PUSH1 0x9C JUMP JUMPDEST PUSH2 0x4D2 ADD SWAP1 JUMP JUMPDEST PUSH1 0x1 ADD SWAP1 JUMP INVALID LOG2 PUSH6 0x627A7A723158 KECCAK256 DUP7 RETURNDATACOPY MSTORE8 CREATE 0xda SELFBALANCE 0x4a SLT PUSH22 0xD583D88852313FE053941E79BDDD5279ABD812B31E02 0xc PUSH5 0x736F6C6343 STOP SDIV 0xc STOP ORIGIN ",
"sourceMap": "632:346:2:-;;;;8:9:-1;5:2;;;30:1;27;20:12;5:2;632:346:2;;;;;;;;;;;;;;;;;;;;;;;;833:143;;;;;;13:2:-1;8:3;5:11;2:2;;;29:1;26;19:12;2:2;-1:-1;833:143:2;;:::i;:::-;;;;;;;;;;;;;;;;694:133;;;;;;13:2:-1;8:3;5:11;2:2;;;29:1;26;19:12;2:2;-1:-1;694:133:2;;:::i;833:143::-;917:14;954:15;:1;:13;:15::i;:::-;947:22;833:143;-1:-1:-1;;833:143:2:o;694:133::-;773:14;810:10;:1;:8;:10::i;842:147:1:-;704:4;965:17;;842:147::o;715:121::-;828:1;824:5;;715:121::o"
}
}
},
"sources": {
"TestLibDummy.sol": {
"id": 2
},
"LibDummy.sol": {
"id": 1
}
},
"sourceCodes": {
"TestLibDummy.sol": "/*\n\n Copyright 2019 ZeroEx Intl.\n\n Licensed under the Apache License, Version 2.0 (the \"License\");\n you may not use this file except in compliance with the License.\n You may obtain a copy of the License at\n\n http://www.apache.org/licenses/LICENSE-2.0\n\n Unless required by applicable law or agreed to in writing, software\n distributed under the License is distributed on an \"AS IS\" BASIS,\n WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n See the License for the specific language governing permissions and\n limitations under the License.\n\n*/\n\npragma solidity ^0.5.5;\n\nimport \"./LibDummy.sol\";\n\n\ncontract TestLibDummy {\n\n using LibDummy for uint256;\n\n function publicAddOne (uint256 x)\n public\n pure\n returns (uint256 result)\n {\n return x.addOne();\n }\n\n function publicAddConstant (uint256 x)\n public\n pure\n returns (uint256 result)\n {\n return x.addConstant();\n }\n}\n",
"LibDummy.sol": "/*\n\n Copyright 2019 ZeroEx Intl.\n\n Licensed under the Apache License, Version 2.0 (the \"License\");\n you may not use this file except in compliance with the License.\n You may obtain a copy of the License at\n\n http://www.apache.org/licenses/LICENSE-2.0\n\n Unless required by applicable law or agreed to in writing, software\n distributed under the License is distributed on an \"AS IS\" BASIS,\n WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n See the License for the specific language governing permissions and\n limitations under the License.\n\n*/\n\npragma solidity ^0.5.5;\n\n\nlibrary LibDummy {\n\n using LibDummy for uint256;\n uint256 constant internal SOME_CONSTANT = 1234;\n\n function addOne (uint256 x)\n internal\n pure\n returns (uint256 sum)\n {\n return x + 1;\n }\n\n function addConstant (uint256 x)\n internal\n pure\n returns (uint256 someConstant)\n {\n return x + SOME_CONSTANT;\n }\n}\n"
},
"sourceTreeHashHex": "0xd7efa9dfeb2bbdec2bead8b892d1288c1398b34216d26c6a48bffb25c692bbc0",
"compiler": {
"name": "solc",
"version": "soljson-v0.5.12+commit.7709ece9.js",
"settings": {
"optimizer": {
"enabled": true,
"runs": 1000000,
"details": {
"yul": true,
"deduplicate": true,
"cse": true,
"constantOptimizer": true
}
},
"outputSelection": {
"*": {
"*": [
"abi",
"evm.bytecode.object",
"evm.bytecode.sourceMap",
"evm.deployedBytecode.object",
"evm.deployedBytecode.sourceMap",
"devdoc"
]
}
},
"evmVersion": "constantinople",
"remappings": []
}
},
"chains": {}
}

View File

@ -1,281 +0,0 @@
/*
Copyright 2019 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 experimental ABIEncoderV2;
pragma solidity ^0.5.5;
contract AbiGenDummy
{
uint256 constant internal SOME_CONSTANT = 1234;
string constant internal REVERT_REASON = "REVERT_WITH_CONSTANT";
string constant internal REQUIRE_REASON = "REQUIRE_WITH_CONSTANT";
function simplePureFunction ()
public
pure
returns (uint256 result)
{
return 1;
}
function simplePureFunctionWithInput (uint256 x)
public
pure
returns (uint256 sum)
{
return 1 + x;
}
function pureFunctionWithConstant ()
public
pure
returns (uint256 someConstant)
{
return SOME_CONSTANT;
}
function simpleRevert ()
public
pure
{
revert("SIMPLE_REVERT");
}
function revertWithConstant ()
public
pure
{
revert(REVERT_REASON);
}
function simpleRequire ()
public
pure
{
require(0 > 1, "SIMPLE_REQUIRE");
}
function requireWithConstant ()
public
pure
{
require(0 > 1, REQUIRE_REASON);
}
/// @dev test that devdocs will be generated and
/// that multiline devdocs will look okay
/// @param hash description of some hash. Let's make this line super long to demonstrate hanging indents for method params. It has to be more than one hundred twenty columns.
/// @param v some v, recovery id
/// @param r ECDSA r output
/// @param s ECDSA s output
/// @return the signerAddress that created this signature. this line too is super long in order to demonstrate the proper hanging indentation in generated code.
function ecrecoverFn(bytes32 hash, uint8 v, bytes32 r, bytes32 s)
public
pure
returns (address signerAddress)
{
bytes memory prefix = "\x19Ethereum Signed Message:\n32";
bytes32 prefixedHash = keccak256(abi.encodePacked(prefix, hash));
return ecrecover(prefixedHash, v, r, s);
}
// test: generated code should normalize address inputs to lowercase
// add extra inputs to make sure it works with address in any position
function withAddressInput(address x, uint256 a, uint256 b, address y, uint256 c)
public
pure
returns (address z)
{
return x;
}
function acceptsBytes(bytes memory a) public pure {}
/// @dev a method that accepts an array of bytes
/// @param a the array of bytes being accepted
function acceptsAnArrayOfBytes(bytes[] memory a) public pure {}
struct Struct {
bytes someBytes;
uint32 anInteger;
bytes[] aDynamicArrayOfBytes;
string aString;
}
function structInput(Struct memory s) public pure {}
/// @dev a method that returns a struct
/// @return a Struct struct
function structOutput() public pure returns(Struct memory s) {
bytes[] memory byteArray = new bytes[](2);
byteArray[0] = "0x123";
byteArray[1] = "0x321";
return Struct({
someBytes: "0x123",
anInteger: 5,
aDynamicArrayOfBytes: byteArray,
aString: "abc"
});
}
function methodReturningArrayOfStructs() public pure returns(Struct[] memory) {}
function methodAcceptingArrayOfStructs(Struct[] memory) public pure {}
function methodAcceptingArrayOfArrayOfStructs(Struct[][] memory) public pure {}
struct NestedStruct {
Struct innerStruct;
string description;
}
function nestedStructInput(NestedStruct memory n) public pure {}
function nestedStructOutput() public pure returns(NestedStruct memory) {}
struct StructNotDirectlyUsedAnywhere {
uint256 aField;
}
struct NestedStructWithInnerStructNotUsedElsewhere {
StructNotDirectlyUsedAnywhere innerStruct;
}
function methodUsingNestedStructWithInnerStructNotUsedElsewhere()
public pure returns(NestedStructWithInnerStructNotUsedElsewhere memory)
{}
uint someState;
function nonPureMethod() public returns(uint) { return someState += 1; }
function nonPureMethodThatReturnsNothing() public { someState += 1; }
function methodReturningMultipleValues()
public pure returns (uint256, string memory)
{
return (1, "hello");
}
function overloadedMethod(int a) public pure {}
function overloadedMethod(string memory a) public pure {}
event Withdrawal(address indexed _owner, uint _value);
function withdraw(uint wad) public {
emit Withdrawal(msg.sender, wad);
}
event SimpleEvent(bytes someBytes, string someString);
function emitSimpleEvent() public {
emit SimpleEvent(
hex'12345678',
"lorem"
);
}
// begin tests for `decodeTransactionData`, `decodeReturnData`
/// @dev complex input is dynamic and more difficult to decode than simple input.
struct ComplexInput {
uint256 foo;
bytes bar;
string car;
}
/// @dev complex input is dynamic and more difficult to decode than simple input.
struct ComplexOutput {
ComplexInput input;
bytes lorem;
bytes ipsum;
string dolor;
}
/// @dev Tests decoding when both input and output are empty.
function noInputNoOutput()
public
pure
{
// NOP
require(true == true);
}
/// @dev Tests decoding when input is empty and output is non-empty.
function noInputSimpleOutput()
public
pure
returns (uint256)
{
return 1991;
}
/// @dev Tests decoding when input is not empty but output is empty.
function simpleInputNoOutput(uint256)
public
pure
{
// NOP
require(true == true);
}
/// @dev Tests decoding when both input and output are non-empty.
function simpleInputSimpleOutput(uint256)
public
pure
returns (uint256)
{
return 1991;
}
/// @dev Tests decoding when the input and output are complex.
function complexInputComplexOutput(ComplexInput memory complexInput)
public
pure
returns (ComplexOutput memory)
{
return ComplexOutput({
input: complexInput,
lorem: hex'12345678',
ipsum: hex'87654321',
dolor: "amet"
});
}
/// @dev Tests decoding when the input and output are complex and have more than one argument.
function multiInputMultiOutput(
uint256,
bytes memory,
string memory
)
public
pure
returns (
bytes memory,
bytes memory,
string memory
)
{
return (
hex'12345678',
hex'87654321',
"amet"
);
}
// end tests for `decodeTransactionData`, `decodeReturnData`
}

View File

@ -1,42 +0,0 @@
/*
Copyright 2019 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.5.5;
library LibDummy {
using LibDummy for uint256;
uint256 constant internal SOME_CONSTANT = 1234;
function addOne (uint256 x)
internal
pure
returns (uint256 sum)
{
return x + 1;
}
function addConstant (uint256 x)
internal
pure
returns (uint256 someConstant)
{
return x + SOME_CONSTANT;
}
}

View File

@ -1,43 +0,0 @@
/*
Copyright 2019 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.5.5;
import "./LibDummy.sol";
contract TestLibDummy {
using LibDummy for uint256;
function publicAddOne (uint256 x)
public
pure
returns (uint256 result)
{
return x.addOne();
}
function publicAddConstant (uint256 x)
public
pure
returns (uint256 result)
{
return x.addConstant();
}
}

View File

@ -1,7 +0,0 @@
[MESSAGES CONTROL]
disable=C0330,line-too-long,fixme,too-few-public-methods,too-many-ancestors,duplicate-code,blacklisted-name
# C0330 is "bad hanging indent". we use indents per `black`.
[BASIC]
argument-rgx=[a-z_][a-z0-9_]{0,31}$
# above differs from the default only in that it allows 2-character names

View File

@ -1,8 +0,0 @@
black
eth_utils
hexbytes
mypy
mypy_extensions
pylint
web3
../../python-packages/contract_wrappers

File diff suppressed because one or more lines are too long

View File

@ -1,109 +0,0 @@
"""Generated wrapper for LibDummy Solidity contract."""
# pylint: disable=too-many-arguments
import json
from typing import ( # pylint: disable=unused-import
Any,
List,
Optional,
Tuple,
Union,
)
from eth_utils import to_checksum_address
from mypy_extensions import TypedDict # pylint: disable=unused-import
from hexbytes import HexBytes
from web3 import Web3
from web3.contract import ContractFunction
from web3.datastructures import AttributeDict
from web3.providers.base import BaseProvider
from zero_ex.contract_wrappers.bases import ContractMethod, Validator
from zero_ex.contract_wrappers.tx_params import TxParams
# Try to import a custom validator class definition; if there isn't one,
# declare one that we can instantiate for the default argument to the
# constructor for LibDummy below.
try:
# both mypy and pylint complain about what we're doing here, but this
# works just fine, so their messages have been disabled here.
from . import ( # type: ignore # pylint: disable=import-self
LibDummyValidator,
)
except ImportError:
class LibDummyValidator( # type: ignore
Validator
):
"""No-op input validator."""
try:
from .middleware import MIDDLEWARE # type: ignore
except ImportError:
pass
# pylint: disable=too-many-public-methods,too-many-instance-attributes
class LibDummy:
"""Wrapper class for LibDummy Solidity contract."""
def __init__(
self,
web3_or_provider: Union[Web3, BaseProvider],
contract_address: str,
validator: LibDummyValidator = None,
):
"""Get an instance of wrapper for smart contract.
:param web3_or_provider: Either an instance of `web3.Web3`:code: or
`web3.providers.base.BaseProvider`:code:
:param contract_address: where the contract has been deployed
:param validator: for validation of method inputs.
"""
# pylint: disable=too-many-statements
self.contract_address = contract_address
if not validator:
validator = LibDummyValidator(web3_or_provider, contract_address)
web3 = None
if isinstance(web3_or_provider, BaseProvider):
web3 = Web3(web3_or_provider)
elif isinstance(web3_or_provider, Web3):
web3 = web3_or_provider
else:
raise TypeError(
"Expected parameter 'web3_or_provider' to be an instance of either"
+ " Web3 or BaseProvider"
)
# if any middleware was imported, inject it
try:
MIDDLEWARE
except NameError:
pass
else:
try:
for middleware in MIDDLEWARE:
web3.middleware_onion.inject(
middleware["function"], layer=middleware["layer"],
)
except ValueError as value_error:
if value_error.args == (
"You can't add the same un-named instance twice",
):
pass
self._web3_eth = web3.eth
@staticmethod
def abi():
"""Return the ABI to the underlying contract."""
return json.loads("[]") # noqa: E501 (line-too-long)
# pylint: disable=too-many-lines

View File

@ -1,230 +0,0 @@
"""Generated wrapper for TestLibDummy Solidity contract."""
# pylint: disable=too-many-arguments
import json
from typing import ( # pylint: disable=unused-import
Any,
List,
Optional,
Tuple,
Union,
)
from eth_utils import to_checksum_address
from mypy_extensions import TypedDict # pylint: disable=unused-import
from hexbytes import HexBytes
from web3 import Web3
from web3.contract import ContractFunction
from web3.datastructures import AttributeDict
from web3.providers.base import BaseProvider
from zero_ex.contract_wrappers.bases import ContractMethod, Validator
from zero_ex.contract_wrappers.tx_params import TxParams
# Try to import a custom validator class definition; if there isn't one,
# declare one that we can instantiate for the default argument to the
# constructor for TestLibDummy below.
try:
# both mypy and pylint complain about what we're doing here, but this
# works just fine, so their messages have been disabled here.
from . import ( # type: ignore # pylint: disable=import-self
TestLibDummyValidator,
)
except ImportError:
class TestLibDummyValidator( # type: ignore
Validator
):
"""No-op input validator."""
try:
from .middleware import MIDDLEWARE # type: ignore
except ImportError:
pass
class PublicAddConstantMethod(ContractMethod): # pylint: disable=invalid-name
"""Various interfaces to the publicAddConstant method."""
def __init__(
self,
web3_or_provider: Union[Web3, BaseProvider],
contract_address: str,
contract_function: ContractFunction,
validator: Validator = None,
):
"""Persist instance data."""
super().__init__(web3_or_provider, contract_address, validator)
self._underlying_method = contract_function
def validate_and_normalize_inputs(self, x: int):
"""Validate the inputs to the publicAddConstant method."""
self.validator.assert_valid(
method_name="publicAddConstant",
parameter_name="x",
argument_value=x,
)
# safeguard against fractional inputs
x = int(x)
return x
def call(self, x: int, tx_params: Optional[TxParams] = None) -> int:
"""Execute underlying contract method via eth_call.
:param tx_params: transaction parameters
"""
(x) = self.validate_and_normalize_inputs(x)
tx_params = super().normalize_tx_params(tx_params)
returned = self._underlying_method(x).call(tx_params.as_dict())
return int(returned)
def estimate_gas(
self, x: int, tx_params: Optional[TxParams] = None
) -> int:
"""Estimate gas consumption of method call."""
(x) = self.validate_and_normalize_inputs(x)
tx_params = super().normalize_tx_params(tx_params)
return self._underlying_method(x).estimateGas(tx_params.as_dict())
class PublicAddOneMethod(ContractMethod): # pylint: disable=invalid-name
"""Various interfaces to the publicAddOne method."""
def __init__(
self,
web3_or_provider: Union[Web3, BaseProvider],
contract_address: str,
contract_function: ContractFunction,
validator: Validator = None,
):
"""Persist instance data."""
super().__init__(web3_or_provider, contract_address, validator)
self._underlying_method = contract_function
def validate_and_normalize_inputs(self, x: int):
"""Validate the inputs to the publicAddOne method."""
self.validator.assert_valid(
method_name="publicAddOne", parameter_name="x", argument_value=x,
)
# safeguard against fractional inputs
x = int(x)
return x
def call(self, x: int, tx_params: Optional[TxParams] = None) -> int:
"""Execute underlying contract method via eth_call.
:param tx_params: transaction parameters
"""
(x) = self.validate_and_normalize_inputs(x)
tx_params = super().normalize_tx_params(tx_params)
returned = self._underlying_method(x).call(tx_params.as_dict())
return int(returned)
def estimate_gas(
self, x: int, tx_params: Optional[TxParams] = None
) -> int:
"""Estimate gas consumption of method call."""
(x) = self.validate_and_normalize_inputs(x)
tx_params = super().normalize_tx_params(tx_params)
return self._underlying_method(x).estimateGas(tx_params.as_dict())
# pylint: disable=too-many-public-methods,too-many-instance-attributes
class TestLibDummy:
"""Wrapper class for TestLibDummy Solidity contract."""
public_add_constant: PublicAddConstantMethod
"""Constructor-initialized instance of
:class:`PublicAddConstantMethod`.
"""
public_add_one: PublicAddOneMethod
"""Constructor-initialized instance of
:class:`PublicAddOneMethod`.
"""
def __init__(
self,
web3_or_provider: Union[Web3, BaseProvider],
contract_address: str,
validator: TestLibDummyValidator = None,
):
"""Get an instance of wrapper for smart contract.
:param web3_or_provider: Either an instance of `web3.Web3`:code: or
`web3.providers.base.BaseProvider`:code:
:param contract_address: where the contract has been deployed
:param validator: for validation of method inputs.
"""
# pylint: disable=too-many-statements
self.contract_address = contract_address
if not validator:
validator = TestLibDummyValidator(
web3_or_provider, contract_address
)
web3 = None
if isinstance(web3_or_provider, BaseProvider):
web3 = Web3(web3_or_provider)
elif isinstance(web3_or_provider, Web3):
web3 = web3_or_provider
else:
raise TypeError(
"Expected parameter 'web3_or_provider' to be an instance of either"
+ " Web3 or BaseProvider"
)
# if any middleware was imported, inject it
try:
MIDDLEWARE
except NameError:
pass
else:
try:
for middleware in MIDDLEWARE:
web3.middleware_onion.inject(
middleware["function"], layer=middleware["layer"],
)
except ValueError as value_error:
if value_error.args == (
"You can't add the same un-named instance twice",
):
pass
self._web3_eth = web3.eth
functions = self._web3_eth.contract(
address=to_checksum_address(contract_address),
abi=TestLibDummy.abi(),
).functions
self.public_add_constant = PublicAddConstantMethod(
web3_or_provider,
contract_address,
functions.publicAddConstant,
validator,
)
self.public_add_one = PublicAddOneMethod(
web3_or_provider,
contract_address,
functions.publicAddOne,
validator,
)
@staticmethod
def abi():
"""Return the ABI to the underlying contract."""
return json.loads(
'[{"constant":true,"inputs":[{"internalType":"uint256","name":"x","type":"uint256"}],"name":"publicAddConstant","outputs":[{"internalType":"uint256","name":"result","type":"uint256"}],"payable":false,"stateMutability":"pure","type":"function"},{"constant":true,"inputs":[{"internalType":"uint256","name":"x","type":"uint256"}],"name":"publicAddOne","outputs":[{"internalType":"uint256","name":"result","type":"uint256"}],"payable":false,"stateMutability":"pure","type":"function"}]' # noqa: E501 (line-too-long)
)
# pylint: disable=too-many-lines

File diff suppressed because one or more lines are too long

View File

@ -1,258 +0,0 @@
// tslint:disable:no-consecutive-blank-lines ordered-imports align trailing-comma enum-naming
// tslint:disable:whitespace no-unbound-method no-trailing-whitespace
// tslint:disable:no-unused-variable
import {
AwaitTransactionSuccessOpts,
ContractFunctionObj,
ContractTxFunctionObj,
SendTransactionOpts,
BaseContract,
PromiseWithTransactionHash,
methodAbiToFunctionSignature,
linkLibrariesInBytecode,
} from '@0x/base-contract';
import { schemas } from '@0x/json-schemas';
import {
BlockParam,
BlockParamLiteral,
BlockRange,
CallData,
ContractAbi,
ContractArtifact,
DecodedLogArgs,
MethodAbi,
TransactionReceiptWithDecodedLogs,
TxData,
TxDataPayable,
SupportedProvider,
} from 'ethereum-types';
import { BigNumber, classUtils, hexUtils, logUtils, providerUtils } from '@0x/utils';
import { EventCallback, IndexedFilterValues, SimpleContractArtifact } from '@0x/types';
import { Web3Wrapper } from '@0x/web3-wrapper';
import { assert } from '@0x/assert';
import * as ethers from 'ethers';
// tslint:enable:no-unused-variable
/* istanbul ignore next */
// tslint:disable:array-type
// tslint:disable:no-parameter-reassignment
// tslint:disable-next-line:class-name
export class LibDummyContract extends BaseContract {
/**
* @ignore
*/
public static deployedBytecode: string | undefined;
public static contractName = 'LibDummy';
private readonly _methodABIIndex: { [name: string]: number } = {};
public static async deployFrom0xArtifactAsync(
artifact: ContractArtifact | SimpleContractArtifact,
supportedProvider: SupportedProvider,
txDefaults: Partial<TxData>,
logDecodeDependencies: { [contractName: string]: ContractArtifact | SimpleContractArtifact },
): Promise<LibDummyContract> {
assert.doesConformToSchema('txDefaults', txDefaults, schemas.txDataSchema, [
schemas.addressSchema,
schemas.numberSchema,
schemas.jsNumber,
]);
if (artifact.compilerOutput === undefined) {
throw new Error('Compiler output not found in the artifact file');
}
const provider = providerUtils.standardizeOrThrow(supportedProvider);
const bytecode = artifact.compilerOutput.evm.bytecode.object;
const abi = artifact.compilerOutput.abi;
const logDecodeDependenciesAbiOnly: { [contractName: string]: ContractAbi } = {};
if (Object.keys(logDecodeDependencies) !== undefined) {
for (const key of Object.keys(logDecodeDependencies)) {
logDecodeDependenciesAbiOnly[key] = logDecodeDependencies[key].compilerOutput.abi;
}
}
return LibDummyContract.deployAsync(bytecode, abi, provider, txDefaults, logDecodeDependenciesAbiOnly);
}
public static async deployWithLibrariesFrom0xArtifactAsync(
artifact: ContractArtifact,
libraryArtifacts: { [libraryName: string]: ContractArtifact },
supportedProvider: SupportedProvider,
txDefaults: Partial<TxData>,
logDecodeDependencies: { [contractName: string]: ContractArtifact | SimpleContractArtifact },
): Promise<LibDummyContract> {
assert.doesConformToSchema('txDefaults', txDefaults, schemas.txDataSchema, [
schemas.addressSchema,
schemas.numberSchema,
schemas.jsNumber,
]);
if (artifact.compilerOutput === undefined) {
throw new Error('Compiler output not found in the artifact file');
}
const provider = providerUtils.standardizeOrThrow(supportedProvider);
const abi = artifact.compilerOutput.abi;
const logDecodeDependenciesAbiOnly: { [contractName: string]: ContractAbi } = {};
if (Object.keys(logDecodeDependencies) !== undefined) {
for (const key of Object.keys(logDecodeDependencies)) {
logDecodeDependenciesAbiOnly[key] = logDecodeDependencies[key].compilerOutput.abi;
}
}
const libraryAddresses = await LibDummyContract._deployLibrariesAsync(
artifact,
libraryArtifacts,
new Web3Wrapper(provider),
txDefaults,
);
const bytecode = linkLibrariesInBytecode(artifact, libraryAddresses);
return LibDummyContract.deployAsync(bytecode, abi, provider, txDefaults, logDecodeDependenciesAbiOnly);
}
public static async deployAsync(
bytecode: string,
abi: ContractAbi,
supportedProvider: SupportedProvider,
txDefaults: Partial<TxData>,
logDecodeDependencies: { [contractName: string]: ContractAbi },
): Promise<LibDummyContract> {
assert.isHexString('bytecode', bytecode);
assert.doesConformToSchema('txDefaults', txDefaults, schemas.txDataSchema, [
schemas.addressSchema,
schemas.numberSchema,
schemas.jsNumber,
]);
const provider = providerUtils.standardizeOrThrow(supportedProvider);
const constructorAbi = BaseContract._lookupConstructorAbi(abi);
[] = BaseContract._formatABIDataItemList(constructorAbi.inputs, [], BaseContract._bigNumberToString);
const iface = new ethers.utils.Interface(abi);
const deployInfo = iface.deployFunction;
const txData = deployInfo.encode(bytecode, []);
const web3Wrapper = new Web3Wrapper(provider);
const txDataWithDefaults = await BaseContract._applyDefaultsToContractTxDataAsync(
{
data: txData,
...txDefaults,
},
web3Wrapper.estimateGasAsync.bind(web3Wrapper),
);
const txHash = await web3Wrapper.sendTransactionAsync(txDataWithDefaults);
logUtils.log(`transactionHash: ${txHash}`);
const txReceipt = await web3Wrapper.awaitTransactionSuccessAsync(txHash);
logUtils.log(`LibDummy successfully deployed at ${txReceipt.contractAddress}`);
const contractInstance = new LibDummyContract(
txReceipt.contractAddress as string,
provider,
txDefaults,
logDecodeDependencies,
);
contractInstance.constructorArgs = [];
return contractInstance;
}
/**
* @returns The contract ABI
*/
public static ABI(): ContractAbi {
const abi = [] as ContractAbi;
return abi;
}
protected static async _deployLibrariesAsync(
artifact: ContractArtifact,
libraryArtifacts: { [libraryName: string]: ContractArtifact },
web3Wrapper: Web3Wrapper,
txDefaults: Partial<TxData>,
libraryAddresses: { [libraryName: string]: string } = {},
): Promise<{ [libraryName: string]: string }> {
const links = artifact.compilerOutput.evm.bytecode.linkReferences;
// Go through all linked libraries, recursively deploying them if necessary.
for (const link of Object.values(links)) {
for (const libraryName of Object.keys(link)) {
if (!libraryAddresses[libraryName]) {
// Library not yet deployed.
const libraryArtifact = libraryArtifacts[libraryName];
if (!libraryArtifact) {
throw new Error(`Missing artifact for linked library "${libraryName}"`);
}
// Deploy any dependent libraries used by this library.
await LibDummyContract._deployLibrariesAsync(
libraryArtifact,
libraryArtifacts,
web3Wrapper,
txDefaults,
libraryAddresses,
);
// Deploy this library.
const linkedLibraryBytecode = linkLibrariesInBytecode(libraryArtifact, libraryAddresses);
const txDataWithDefaults = await BaseContract._applyDefaultsToContractTxDataAsync(
{
data: linkedLibraryBytecode,
...txDefaults,
},
web3Wrapper.estimateGasAsync.bind(web3Wrapper),
);
const txHash = await web3Wrapper.sendTransactionAsync(txDataWithDefaults);
logUtils.log(`transactionHash: ${txHash}`);
const { contractAddress } = await web3Wrapper.awaitTransactionSuccessAsync(txHash);
logUtils.log(`${libraryArtifact.contractName} successfully deployed at ${contractAddress}`);
libraryAddresses[libraryArtifact.contractName] = contractAddress as string;
}
}
}
return libraryAddresses;
}
public getFunctionSignature(methodName: string): string {
const index = this._methodABIIndex[methodName];
const methodAbi = LibDummyContract.ABI()[index] as MethodAbi; // tslint:disable-line:no-unnecessary-type-assertion
const functionSignature = methodAbiToFunctionSignature(methodAbi);
return functionSignature;
}
public getABIDecodedTransactionData<T>(methodName: string, callData: string): T {
const functionSignature = this.getFunctionSignature(methodName);
const self = (this as any) as LibDummyContract;
const abiEncoder = self._lookupAbiEncoder(functionSignature);
const abiDecodedCallData = abiEncoder.strictDecode<T>(callData);
return abiDecodedCallData;
}
public getABIDecodedReturnData<T>(methodName: string, callData: string): T {
const functionSignature = this.getFunctionSignature(methodName);
const self = (this as any) as LibDummyContract;
const abiEncoder = self._lookupAbiEncoder(functionSignature);
const abiDecodedCallData = abiEncoder.strictDecodeReturnValue<T>(callData);
return abiDecodedCallData;
}
public getSelector(methodName: string): string {
const functionSignature = this.getFunctionSignature(methodName);
const self = (this as any) as LibDummyContract;
const abiEncoder = self._lookupAbiEncoder(functionSignature);
return abiEncoder.getSelector();
}
constructor(
address: string,
supportedProvider: SupportedProvider,
txDefaults?: Partial<TxData>,
logDecodeDependencies?: { [contractName: string]: ContractAbi },
deployedBytecode: string | undefined = LibDummyContract.deployedBytecode,
) {
super(
'LibDummy',
LibDummyContract.ABI(),
address,
supportedProvider,
txDefaults,
logDecodeDependencies,
deployedBytecode,
);
classUtils.bindAll(this, ['_abiEncoderByFunctionSignature', 'address', '_web3Wrapper']);
LibDummyContract.ABI().forEach((item, index) => {
if (item.type === 'function') {
const methodAbi = item as MethodAbi;
this._methodABIIndex[methodAbi.name] = index;
}
});
}
}
// tslint:disable:max-file-line-count
// tslint:enable:no-unbound-method no-parameter-reassignment no-consecutive-blank-lines ordered-imports align
// tslint:enable:trailing-comma whitespace no-trailing-whitespace

View File

@ -1,351 +0,0 @@
// tslint:disable:no-consecutive-blank-lines ordered-imports align trailing-comma enum-naming
// tslint:disable:whitespace no-unbound-method no-trailing-whitespace
// tslint:disable:no-unused-variable
import {
AwaitTransactionSuccessOpts,
ContractFunctionObj,
ContractTxFunctionObj,
SendTransactionOpts,
BaseContract,
PromiseWithTransactionHash,
methodAbiToFunctionSignature,
linkLibrariesInBytecode,
} from '@0x/base-contract';
import { schemas } from '@0x/json-schemas';
import {
BlockParam,
BlockParamLiteral,
BlockRange,
CallData,
ContractAbi,
ContractArtifact,
DecodedLogArgs,
MethodAbi,
TransactionReceiptWithDecodedLogs,
TxData,
TxDataPayable,
SupportedProvider,
} from 'ethereum-types';
import { BigNumber, classUtils, hexUtils, logUtils, providerUtils } from '@0x/utils';
import { EventCallback, IndexedFilterValues, SimpleContractArtifact } from '@0x/types';
import { Web3Wrapper } from '@0x/web3-wrapper';
import { assert } from '@0x/assert';
import * as ethers from 'ethers';
// tslint:enable:no-unused-variable
/* istanbul ignore next */
// tslint:disable:array-type
// tslint:disable:no-parameter-reassignment
// tslint:disable-next-line:class-name
export class TestLibDummyContract extends BaseContract {
/**
* @ignore
*/
public static deployedBytecode =
'0x6080604052348015600f57600080fd5b506004361060325760003560e01c806322935e921460375780632b82fdf0146063575b600080fd5b605160048036036020811015604b57600080fd5b5035607d565b60408051918252519081900360200190f35b605160048036036020811015607757600080fd5b5035608c565b60006086826095565b92915050565b6000608682609c565b6104d20190565b6001019056fea265627a7a72315820863e53f0da474a1275d583d88852313fe053941e79bddd5279abd812b31e020c64736f6c634300050c0032';
public static contractName = 'TestLibDummy';
private readonly _methodABIIndex: { [name: string]: number } = {};
public static async deployFrom0xArtifactAsync(
artifact: ContractArtifact | SimpleContractArtifact,
supportedProvider: SupportedProvider,
txDefaults: Partial<TxData>,
logDecodeDependencies: { [contractName: string]: ContractArtifact | SimpleContractArtifact },
): Promise<TestLibDummyContract> {
assert.doesConformToSchema('txDefaults', txDefaults, schemas.txDataSchema, [
schemas.addressSchema,
schemas.numberSchema,
schemas.jsNumber,
]);
if (artifact.compilerOutput === undefined) {
throw new Error('Compiler output not found in the artifact file');
}
const provider = providerUtils.standardizeOrThrow(supportedProvider);
const bytecode = artifact.compilerOutput.evm.bytecode.object;
const abi = artifact.compilerOutput.abi;
const logDecodeDependenciesAbiOnly: { [contractName: string]: ContractAbi } = {};
if (Object.keys(logDecodeDependencies) !== undefined) {
for (const key of Object.keys(logDecodeDependencies)) {
logDecodeDependenciesAbiOnly[key] = logDecodeDependencies[key].compilerOutput.abi;
}
}
return TestLibDummyContract.deployAsync(bytecode, abi, provider, txDefaults, logDecodeDependenciesAbiOnly);
}
public static async deployWithLibrariesFrom0xArtifactAsync(
artifact: ContractArtifact,
libraryArtifacts: { [libraryName: string]: ContractArtifact },
supportedProvider: SupportedProvider,
txDefaults: Partial<TxData>,
logDecodeDependencies: { [contractName: string]: ContractArtifact | SimpleContractArtifact },
): Promise<TestLibDummyContract> {
assert.doesConformToSchema('txDefaults', txDefaults, schemas.txDataSchema, [
schemas.addressSchema,
schemas.numberSchema,
schemas.jsNumber,
]);
if (artifact.compilerOutput === undefined) {
throw new Error('Compiler output not found in the artifact file');
}
const provider = providerUtils.standardizeOrThrow(supportedProvider);
const abi = artifact.compilerOutput.abi;
const logDecodeDependenciesAbiOnly: { [contractName: string]: ContractAbi } = {};
if (Object.keys(logDecodeDependencies) !== undefined) {
for (const key of Object.keys(logDecodeDependencies)) {
logDecodeDependenciesAbiOnly[key] = logDecodeDependencies[key].compilerOutput.abi;
}
}
const libraryAddresses = await TestLibDummyContract._deployLibrariesAsync(
artifact,
libraryArtifacts,
new Web3Wrapper(provider),
txDefaults,
);
const bytecode = linkLibrariesInBytecode(artifact, libraryAddresses);
return TestLibDummyContract.deployAsync(bytecode, abi, provider, txDefaults, logDecodeDependenciesAbiOnly);
}
public static async deployAsync(
bytecode: string,
abi: ContractAbi,
supportedProvider: SupportedProvider,
txDefaults: Partial<TxData>,
logDecodeDependencies: { [contractName: string]: ContractAbi },
): Promise<TestLibDummyContract> {
assert.isHexString('bytecode', bytecode);
assert.doesConformToSchema('txDefaults', txDefaults, schemas.txDataSchema, [
schemas.addressSchema,
schemas.numberSchema,
schemas.jsNumber,
]);
const provider = providerUtils.standardizeOrThrow(supportedProvider);
const constructorAbi = BaseContract._lookupConstructorAbi(abi);
[] = BaseContract._formatABIDataItemList(constructorAbi.inputs, [], BaseContract._bigNumberToString);
const iface = new ethers.utils.Interface(abi);
const deployInfo = iface.deployFunction;
const txData = deployInfo.encode(bytecode, []);
const web3Wrapper = new Web3Wrapper(provider);
const txDataWithDefaults = await BaseContract._applyDefaultsToContractTxDataAsync(
{
data: txData,
...txDefaults,
},
web3Wrapper.estimateGasAsync.bind(web3Wrapper),
);
const txHash = await web3Wrapper.sendTransactionAsync(txDataWithDefaults);
logUtils.log(`transactionHash: ${txHash}`);
const txReceipt = await web3Wrapper.awaitTransactionSuccessAsync(txHash);
logUtils.log(`TestLibDummy successfully deployed at ${txReceipt.contractAddress}`);
const contractInstance = new TestLibDummyContract(
txReceipt.contractAddress as string,
provider,
txDefaults,
logDecodeDependencies,
);
contractInstance.constructorArgs = [];
return contractInstance;
}
/**
* @returns The contract ABI
*/
public static ABI(): ContractAbi {
const abi = [
{
constant: true,
inputs: [
{
name: 'x',
type: 'uint256',
},
],
name: 'publicAddConstant',
outputs: [
{
name: 'result',
type: 'uint256',
},
],
payable: false,
stateMutability: 'pure',
type: 'function',
},
{
constant: true,
inputs: [
{
name: 'x',
type: 'uint256',
},
],
name: 'publicAddOne',
outputs: [
{
name: 'result',
type: 'uint256',
},
],
payable: false,
stateMutability: 'pure',
type: 'function',
},
] as ContractAbi;
return abi;
}
protected static async _deployLibrariesAsync(
artifact: ContractArtifact,
libraryArtifacts: { [libraryName: string]: ContractArtifact },
web3Wrapper: Web3Wrapper,
txDefaults: Partial<TxData>,
libraryAddresses: { [libraryName: string]: string } = {},
): Promise<{ [libraryName: string]: string }> {
const links = artifact.compilerOutput.evm.bytecode.linkReferences;
// Go through all linked libraries, recursively deploying them if necessary.
for (const link of Object.values(links)) {
for (const libraryName of Object.keys(link)) {
if (!libraryAddresses[libraryName]) {
// Library not yet deployed.
const libraryArtifact = libraryArtifacts[libraryName];
if (!libraryArtifact) {
throw new Error(`Missing artifact for linked library "${libraryName}"`);
}
// Deploy any dependent libraries used by this library.
await TestLibDummyContract._deployLibrariesAsync(
libraryArtifact,
libraryArtifacts,
web3Wrapper,
txDefaults,
libraryAddresses,
);
// Deploy this library.
const linkedLibraryBytecode = linkLibrariesInBytecode(libraryArtifact, libraryAddresses);
const txDataWithDefaults = await BaseContract._applyDefaultsToContractTxDataAsync(
{
data: linkedLibraryBytecode,
...txDefaults,
},
web3Wrapper.estimateGasAsync.bind(web3Wrapper),
);
const txHash = await web3Wrapper.sendTransactionAsync(txDataWithDefaults);
logUtils.log(`transactionHash: ${txHash}`);
const { contractAddress } = await web3Wrapper.awaitTransactionSuccessAsync(txHash);
logUtils.log(`${libraryArtifact.contractName} successfully deployed at ${contractAddress}`);
libraryAddresses[libraryArtifact.contractName] = contractAddress as string;
}
}
}
return libraryAddresses;
}
public getFunctionSignature(methodName: string): string {
const index = this._methodABIIndex[methodName];
const methodAbi = TestLibDummyContract.ABI()[index] as MethodAbi; // tslint:disable-line:no-unnecessary-type-assertion
const functionSignature = methodAbiToFunctionSignature(methodAbi);
return functionSignature;
}
public getABIDecodedTransactionData<T>(methodName: string, callData: string): T {
const functionSignature = this.getFunctionSignature(methodName);
const self = (this as any) as TestLibDummyContract;
const abiEncoder = self._lookupAbiEncoder(functionSignature);
const abiDecodedCallData = abiEncoder.strictDecode<T>(callData);
return abiDecodedCallData;
}
public getABIDecodedReturnData<T>(methodName: string, callData: string): T {
const functionSignature = this.getFunctionSignature(methodName);
const self = (this as any) as TestLibDummyContract;
const abiEncoder = self._lookupAbiEncoder(functionSignature);
const abiDecodedCallData = abiEncoder.strictDecodeReturnValue<T>(callData);
return abiDecodedCallData;
}
public getSelector(methodName: string): string {
const functionSignature = this.getFunctionSignature(methodName);
const self = (this as any) as TestLibDummyContract;
const abiEncoder = self._lookupAbiEncoder(functionSignature);
return abiEncoder.getSelector();
}
public publicAddConstant(x: BigNumber): ContractFunctionObj<BigNumber> {
const self = (this as any) as TestLibDummyContract;
assert.isBigNumber('x', x);
const functionSignature = 'publicAddConstant(uint256)';
return {
async callAsync(callData: Partial<CallData> = {}, defaultBlock?: BlockParam): Promise<BigNumber> {
BaseContract._assertCallParams(callData, defaultBlock);
let rawCallResult;
if (self._deployedBytecodeIfExists) {
rawCallResult = await self._evmExecAsync(this.getABIEncodedTransactionData());
} else {
rawCallResult = await self._performCallAsync(
{ data: this.getABIEncodedTransactionData(), ...callData },
defaultBlock,
);
}
const abiEncoder = self._lookupAbiEncoder(functionSignature);
BaseContract._throwIfUnexpectedEmptyCallResult(rawCallResult, abiEncoder);
return abiEncoder.strictDecodeReturnValue<BigNumber>(rawCallResult);
},
getABIEncodedTransactionData(): string {
return self._strictEncodeArguments(functionSignature, [x]);
},
};
}
public publicAddOne(x: BigNumber): ContractFunctionObj<BigNumber> {
const self = (this as any) as TestLibDummyContract;
assert.isBigNumber('x', x);
const functionSignature = 'publicAddOne(uint256)';
return {
async callAsync(callData: Partial<CallData> = {}, defaultBlock?: BlockParam): Promise<BigNumber> {
BaseContract._assertCallParams(callData, defaultBlock);
let rawCallResult;
if (self._deployedBytecodeIfExists) {
rawCallResult = await self._evmExecAsync(this.getABIEncodedTransactionData());
} else {
rawCallResult = await self._performCallAsync(
{ data: this.getABIEncodedTransactionData(), ...callData },
defaultBlock,
);
}
const abiEncoder = self._lookupAbiEncoder(functionSignature);
BaseContract._throwIfUnexpectedEmptyCallResult(rawCallResult, abiEncoder);
return abiEncoder.strictDecodeReturnValue<BigNumber>(rawCallResult);
},
getABIEncodedTransactionData(): string {
return self._strictEncodeArguments(functionSignature, [x]);
},
};
}
constructor(
address: string,
supportedProvider: SupportedProvider,
txDefaults?: Partial<TxData>,
logDecodeDependencies?: { [contractName: string]: ContractAbi },
deployedBytecode: string | undefined = TestLibDummyContract.deployedBytecode,
) {
super(
'TestLibDummy',
TestLibDummyContract.ABI(),
address,
supportedProvider,
txDefaults,
logDecodeDependencies,
deployedBytecode,
);
classUtils.bindAll(this, ['_abiEncoderByFunctionSignature', 'address', '_web3Wrapper']);
TestLibDummyContract.ABI().forEach((item, index) => {
if (item.type === 'function') {
const methodAbi = item as MethodAbi;
this._methodABIIndex[methodAbi.name] = index;
}
});
}
}
// tslint:disable:max-file-line-count
// tslint:enable:no-unbound-method no-parameter-reassignment no-consecutive-blank-lines ordered-imports align
// tslint:enable:trailing-comma whitespace no-trailing-whitespace

View File

@ -1,15 +0,0 @@
/*
* -----------------------------------------------------------------------------
* Warning: This file is auto-generated by contracts-gen. Don't edit manually.
* -----------------------------------------------------------------------------
*/
import { ContractArtifact } from 'ethereum-types';
import * as AbiGenDummy from '../../fixtures/artifacts/AbiGenDummy.json';
import * as LibDummy from '../../fixtures/artifacts/LibDummy.json';
import * as TestLibDummy from '../../fixtures/artifacts/TestLibDummy.json';
export const artifacts = {
AbiGenDummy: AbiGenDummy as ContractArtifact,
LibDummy: LibDummy as ContractArtifact,
TestLibDummy: TestLibDummy as ContractArtifact,
};

View File

@ -1,2 +0,0 @@
export { artifacts } from './artifacts';
export * from './wrappers';

View File

@ -1,8 +0,0 @@
/*
* -----------------------------------------------------------------------------
* Warning: This file is auto-generated by contracts-gen. Don't edit manually.
* -----------------------------------------------------------------------------
*/
export * from '../../output/typescript/abi_gen_dummy';
export * from '../../output/typescript/lib_dummy';
export * from '../../output/typescript/test_lib_dummy';

View File

@ -1,329 +0,0 @@
import { ContractFunctionObj } from '@0x/base-contract';
import { BlockchainLifecycle, devConstants, web3Factory } from '@0x/dev-utils';
import { Web3ProviderEngine } from '@0x/subproviders';
import { BigNumber, providerUtils, StringRevertError } from '@0x/utils';
import { BlockParamLiteral, Web3Wrapper } from '@0x/web3-wrapper';
import * as chai from 'chai';
import * as chaiAsPromised from 'chai-as-promised';
import * as ChaiBigNumber from 'chai-bignumber';
import * as dirtyChai from 'dirty-chai';
import * as Sinon from 'sinon';
import {
AbiGenDummyContract,
AbiGenDummyEvents,
AbiGenDummyWithdrawalEventArgs,
artifacts,
TestLibDummyContract,
} from '../src';
const txDefaults = {
from: devConstants.TESTRPC_FIRST_ADDRESS,
gas: devConstants.GAS_LIMIT,
};
const provider: Web3ProviderEngine = web3Factory.getRpcProvider({ shouldUseInProcessGanache: true });
const web3Wrapper = new Web3Wrapper(provider);
chai.config.includeStack = true;
chai.use(ChaiBigNumber());
chai.use(dirtyChai);
chai.use(chaiAsPromised);
const expect = chai.expect;
const blockchainLifecycle = new BlockchainLifecycle(web3Wrapper);
describe('AbiGenDummy Contract', () => {
let abiGenDummy: AbiGenDummyContract;
const runTestAsync = async (
contractMethodName: string,
contractMethod: ContractFunctionObj<any>,
input: any,
output: any,
) => {
const transaction = contractMethod.getABIEncodedTransactionData();
// try decoding transaction
const decodedInput = abiGenDummy.getABIDecodedTransactionData(contractMethodName, transaction);
expect(decodedInput, 'decoded input').to.be.deep.equal(input);
// execute transaction
const rawOutput = await web3Wrapper.callAsync({
to: abiGenDummy.address,
data: transaction,
});
// try decoding output
const decodedOutput = abiGenDummy.getABIDecodedReturnData(contractMethodName, rawOutput);
expect(decodedOutput, 'decoded output').to.be.deep.equal(output);
};
before(async () => {
providerUtils.startProviderEngine(provider);
abiGenDummy = await AbiGenDummyContract.deployFrom0xArtifactAsync(
artifacts.AbiGenDummy,
provider,
txDefaults,
artifacts,
);
await blockchainLifecycle.startAsync();
});
after(async () => {
await blockchainLifecycle.revertAsync();
});
describe('simplePureFunction', () => {
it('should call simplePureFunction', async () => {
const result = await abiGenDummy.simplePureFunction().callAsync();
expect(result).to.deep.equal(new BigNumber(1));
});
});
describe('simplePureFunctionWithInput', () => {
it('should call simplePureFunctionWithInput', async () => {
const result = await abiGenDummy.simplePureFunctionWithInput(new BigNumber(5)).callAsync();
expect(result).to.deep.equal(new BigNumber(6));
});
});
describe('pureFunctionWithConstant', () => {
it('should call pureFunctionWithConstant', async () => {
const result = await abiGenDummy.pureFunctionWithConstant().callAsync();
expect(result).to.deep.equal(new BigNumber(1234));
});
});
describe('simpleRevert', () => {
it('should call simpleRevert', async () => {
expect(abiGenDummy.simpleRevert().callAsync())
.to.eventually.be.rejectedWith(StringRevertError)
.and.deep.equal(new StringRevertError('SIMPLE_REVERT'));
});
});
describe('revertWithConstant', () => {
it('should call revertWithConstant', async () => {
expect(abiGenDummy.revertWithConstant().callAsync())
.to.eventually.be.rejectedWith(StringRevertError)
.and.deep.equal(new StringRevertError('REVERT_WITH_CONSTANT'));
});
});
describe('simpleRequire', () => {
it('should call simpleRequire', async () => {
expect(abiGenDummy.simpleRequire().callAsync())
.to.eventually.be.rejectedWith(StringRevertError)
.and.deep.equal(new StringRevertError('SIMPLE_REQUIRE'));
});
});
describe('requireWithConstant', () => {
it('should call requireWithConstant', async () => {
expect(abiGenDummy.requireWithConstant().callAsync())
.to.eventually.be.rejectedWith(StringRevertError)
.and.deep.equal(new StringRevertError('REQUIRE_WITH_CONSTANT'));
});
});
describe('struct handling', () => {
const sampleStruct = {
aDynamicArrayOfBytes: ['0x3078313233', '0x3078333231'],
anInteger: new BigNumber(5),
aString: 'abc',
someBytes: '0x3078313233',
};
it('should be able to handle struct output', async () => {
const result = await abiGenDummy.structOutput().callAsync();
expect(result).to.deep.equal(sampleStruct);
});
});
describe('ecrecoverFn', () => {
it('should implement ecrecover', async () => {
const signerAddress = devConstants.TESTRPC_FIRST_ADDRESS;
const message = '0x6927e990021d23b1eb7b8789f6a6feaf98fe104bb0cf8259421b79f9a34222b0';
const signature = await web3Wrapper.signMessageAsync(signerAddress, message);
// tslint:disable:custom-no-magic-numbers
const r = `0x${signature.slice(2, 66)}`;
const s = `0x${signature.slice(66, 130)}`;
const v = signature.slice(130, 132);
const v_decimal = parseInt(v, 16) + 27; // v: (0 or 1) => (27 or 28)
// tslint:enable:custom-no-magic-numbers
const result = await abiGenDummy.ecrecoverFn(message, v_decimal, r, s).callAsync();
expect(result).to.equal(signerAddress);
});
});
describe('event subscription', () => {
const indexFilterValues = {};
const emptyCallback = () => {}; // tslint:disable-line:no-empty
let stubs: Sinon.SinonStub[] = [];
afterEach(() => {
stubs.forEach(s => s.restore());
stubs = [];
});
it('should return a subscription token', done => {
const subscriptionToken = abiGenDummy.subscribe(
AbiGenDummyEvents.Withdrawal,
indexFilterValues,
emptyCallback,
);
expect(subscriptionToken).to.be.a('string');
done();
});
it('should allow unsubscribeAll to be called successfully after an error', done => {
abiGenDummy.subscribe(AbiGenDummyEvents.Withdrawal, indexFilterValues, emptyCallback);
stubs.push(
Sinon.stub((abiGenDummy as any)._web3Wrapper, 'getBlockIfExistsAsync').throws(
new Error('JSON RPC error'),
),
);
abiGenDummy.unsubscribeAll();
done();
});
});
describe('getLogsAsync', () => {
const blockRange = {
fromBlock: 0,
toBlock: BlockParamLiteral.Latest,
};
it('should get logs with decoded args emitted by EventWithStruct', async () => {
await abiGenDummy.emitSimpleEvent().awaitTransactionSuccessAsync();
const eventName = AbiGenDummyEvents.SimpleEvent;
const indexFilterValues = {};
const logs = await abiGenDummy.getLogsAsync(eventName, blockRange, indexFilterValues);
expect(logs).to.have.length(1);
expect(logs[0].event).to.be.equal(eventName);
});
it('should only get the logs with the correct event name', async () => {
await abiGenDummy.emitSimpleEvent().awaitTransactionSuccessAsync();
const differentEventName = AbiGenDummyEvents.Withdrawal;
const indexFilterValues = {};
const logs = await abiGenDummy.getLogsAsync(differentEventName, blockRange, indexFilterValues);
expect(logs).to.have.length(0);
});
it('should only get the logs with the correct indexed fields', async () => {
const [addressOne, addressTwo] = await web3Wrapper.getAvailableAddressesAsync();
await abiGenDummy.withdraw(new BigNumber(1)).awaitTransactionSuccessAsync({ from: addressOne });
await abiGenDummy.withdraw(new BigNumber(1)).awaitTransactionSuccessAsync({ from: addressTwo });
const eventName = AbiGenDummyEvents.Withdrawal;
const indexFilterValues = {
_owner: addressOne,
};
const logs = await abiGenDummy.getLogsAsync<AbiGenDummyWithdrawalEventArgs>(
eventName,
blockRange,
indexFilterValues,
);
expect(logs).to.have.length(1);
const args = logs[0].args;
expect(args._owner).to.be.equal(addressOne);
});
});
describe('withAddressInput', () => {
it('should normalize address inputs to lowercase', async () => {
const xAddress = devConstants.TESTRPC_FIRST_ADDRESS.toUpperCase();
const yAddress = devConstants.TESTRPC_FIRST_ADDRESS;
const a = new BigNumber(1);
const b = new BigNumber(2);
const c = new BigNumber(3);
const output = await abiGenDummy.withAddressInput(xAddress, a, b, yAddress, c).callAsync();
expect(output).to.equal(xAddress.toLowerCase());
});
});
describe('Encoding/Decoding Transaction Data and Return Values', () => {
it('should successfully encode/decode (no input / no output)', async () => {
const input = undefined;
const output = undefined;
await runTestAsync('noInputNoOutput', abiGenDummy.noInputNoOutput(), input, output);
});
it('should successfully encode/decode (no input / simple output)', async () => {
const input = undefined;
const output = new BigNumber(1991);
await runTestAsync('noInputSimpleOutput', abiGenDummy.noInputSimpleOutput(), input, output);
});
it('should successfully encode/decode (simple input / no output)', async () => {
const input = new BigNumber(1991);
const output = undefined;
await runTestAsync('simpleInputNoOutput', abiGenDummy.simpleInputNoOutput(input), input, output);
});
it('should successfully encode/decode (simple input / simple output)', async () => {
const input = new BigNumber(16);
const output = new BigNumber(1991);
await runTestAsync('simpleInputSimpleOutput', abiGenDummy.simpleInputSimpleOutput(input), input, output);
});
it('should successfully encode/decode (complex input / complex output)', async () => {
const input = {
foo: new BigNumber(1991),
bar: '0x1234',
car: 'zoom zoom',
};
const output = {
input,
lorem: '0x12345678',
ipsum: '0x87654321',
dolor: 'amet',
};
await runTestAsync(
'complexInputComplexOutput',
abiGenDummy.complexInputComplexOutput(input),
input,
output,
);
});
it('should successfully encode/decode (multi-input / multi-output)', async () => {
const input = [new BigNumber(1991), '0x1234', 'zoom zoom'];
const output = ['0x12345678', '0x87654321', 'amet'];
const transaction = abiGenDummy
.multiInputMultiOutput(input[0] as BigNumber, input[1] as string, input[2] as string)
.getABIEncodedTransactionData();
// try decoding transaction
const decodedInput = abiGenDummy.getABIDecodedTransactionData('multiInputMultiOutput', transaction);
expect(decodedInput, 'decoded input').to.be.deep.equal(input);
// execute transaction
const rawOutput = await web3Wrapper.callAsync({
to: abiGenDummy.address,
data: transaction,
});
// try decoding output
const decodedOutput = abiGenDummy.getABIDecodedReturnData('multiInputMultiOutput', rawOutput);
expect(decodedOutput, 'decoded output').to.be.deep.equal(output);
});
});
describe('awaitTransactionSuccessAsync', async () => {
it('should successfully call the non pure function', async () => {
expect(
abiGenDummy.nonPureMethod().awaitTransactionSuccessAsync({}, { pollingIntervalMs: 10, timeoutMs: 100 }),
).to.be.fulfilled('');
});
});
});
describe('Lib dummy contract', () => {
let libDummy: TestLibDummyContract;
before(async () => {
await blockchainLifecycle.startAsync();
});
after(async () => {
await blockchainLifecycle.revertAsync();
});
before(async () => {
libDummy = await TestLibDummyContract.deployFrom0xArtifactAsync(
artifacts.TestLibDummy,
provider,
txDefaults,
artifacts,
);
});
beforeEach(async () => {
await blockchainLifecycle.startAsync();
});
afterEach(async () => {
await blockchainLifecycle.revertAsync();
});
it('should call a library function', async () => {
const result = await libDummy.publicAddOne(new BigNumber(1)).callAsync();
expect(result).to.deep.equal(new BigNumber(2));
});
it('should call a library function referencing a constant', async () => {
const result = await libDummy.publicAddConstant(new BigNumber(1)).callAsync();
expect(result).to.deep.equal(new BigNumber(1235));
});
});

View File

@ -1,15 +0,0 @@
{
"extends": "../../../tsconfig.json",
"compilerOptions": {
"resolveJsonModule": true,
"outDir": "./test_typescript/lib",
"rootDir": "."
},
"files": [
"./fixtures/artifacts/AbiGenDummy.json",
"./fixtures/artifacts/LibDummy.json",
"./fixtures/artifacts/TestLibDummy.json"
],
"exclude": ["./test_typescript/lib"],
"include": ["./output/typescript/**/*", "./test_typescript/**/*"]
}

View File

@ -1,98 +0,0 @@
import * as chai from 'chai';
import * as dirtyChai from 'dirty-chai';
import * as fs from 'fs';
import 'mocha';
import * as tmp from 'tmp';
import { utils } from '../src/utils';
tmp.setGracefulCleanup(); // remove tmp files even if there are failures
chai.use(dirtyChai);
const expect = chai.expect;
describe('makeOutputFileName()', () => {
it('should handle Metacoin usage', () => {
expect(utils.makeOutputFileName('Metacoin')).to.equal('metacoin');
});
it('should handle special zrx_token case', () => {
expect(utils.makeOutputFileName('ZRXToken')).to.equal('zrx_token');
});
it('should handle special erc_token case', () => {
expect(utils.makeOutputFileName('ERC20Token')).to.equal('erc20_token');
});
});
describe('writeOutputFile()', () => {
let tempFilePath: string;
before(() => {
tempFilePath = tmp.fileSync(
{ discardDescriptor: true }, // close file (so we can update it)
).name;
});
it('should write content to output file', () => {
const content = 'hello world';
utils.writeOutputFile(tempFilePath, content);
expect(fs.readFileSync(tempFilePath).toString()).to.equal(content);
});
});
describe('isOutputFileUpToDate()', () => {
it('should throw ENOENT when there is no abi file', () => {
expect(utils.isOutputFileUpToDate.bind('', 'nonexistant1', ['nonexistant2'])).to.throw('ENOENT');
});
describe('when the abi input file exists', () => {
let abiFile: string;
before(() => {
abiFile = tmp.fileSync(
{ discardDescriptor: true }, // close file (set timestamp)
).name;
});
describe('without an existing output file', () => {
it('should return false', () => {
expect(utils.isOutputFileUpToDate('nonexistant_file', [abiFile])).to.be.false();
});
});
describe('with an existing output file', () => {
let outputFile: string;
before(() => {
outputFile = tmp.fileSync(
{ discardDescriptor: true }, // close file (set timestamp)
).name;
const abiFileModTimeMs = fs.statSync(abiFile).mtimeMs;
const outfileModTimeMs = abiFileModTimeMs + 1;
fs.utimesSync(outputFile, outfileModTimeMs, outfileModTimeMs);
});
it('should return true when output file is newer than abi file', async () => {
expect(utils.isOutputFileUpToDate(outputFile, [abiFile])).to.be.true();
});
it('should return false when output file exists but is older than abi file', () => {
const outFileModTimeMs = fs.statSync(outputFile).mtimeMs;
const abiFileModTimeMs = outFileModTimeMs + 1;
fs.utimesSync(abiFile, abiFileModTimeMs, abiFileModTimeMs);
expect(utils.isOutputFileUpToDate(outputFile, [abiFile])).to.be.false();
});
it('should return false when any source file is newer than output file', () => {
const templateFile = tmp.fileSync(
{ discardDescriptor: true }, // close file (set timestamp)
).name;
const templateFileModTimeMs = fs.statSync(outputFile).mtimeMs + 1;
const abiFileModTimeMs = fs.statSync(outputFile).mtimeMs;
fs.utimesSync(templateFile, templateFileModTimeMs, templateFileModTimeMs);
fs.utimesSync(abiFile, abiFileModTimeMs, abiFileModTimeMs);
expect(utils.isOutputFileUpToDate(outputFile, [abiFile, templateFile])).to.be.false();
});
});
});
});

View File

@ -1,14 +0,0 @@
{
"extends": "../../tsconfig",
"compilerOptions": {
"outDir": "lib",
"rootDir": "."
},
"exclude": [
"./test-cli/**/*",
"./src/artifacts.ts",
"./src/wrappers.ts",
"prior two elements refer to code generated by contracts-gen for test fixture contracts"
],
"include": ["./src/**/*", "./test/*"]
}

View File

@ -1,6 +0,0 @@
{
"extends": ["@0x/tslint-config"],
"linterOptions": {
"exclude": ["./test-cli/fixtures/**/*", "**/lib/**/*"]
}
}

View File

@ -1,9 +0,0 @@
# Blacklist all files
.*
*
# Whitelist lib
!lib/**/*
# Blacklist tests and publish scripts
/lib/test/*
/lib/monorepo_scripts/
# Package specific ignore

View File

@ -1,658 +0,0 @@
[
{
"timestamp": 1594788383,
"version": "3.0.9",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1592969527,
"version": "3.0.8",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1582623685,
"version": "3.0.7",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1581204851,
"version": "3.0.6",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1580988106,
"version": "3.0.5",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1579682890,
"version": "3.0.4",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1578272714,
"version": "3.0.3",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1576540892,
"version": "3.0.2",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1575931811,
"version": "3.0.1",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "3.0.0",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1575296764
},
{
"version": "2.2.0-beta.3",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1575290197
},
{
"version": "2.2.0-beta.2",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1574030254
},
{
"version": "2.2.0-beta.1",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1573159180
},
{
"version": "2.2.0-beta.0",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1570135330
},
{
"timestamp": 1568744790,
"version": "2.1.6",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1567521715,
"version": "2.1.5",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1566446343,
"version": "2.1.4",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1565296576,
"version": "2.1.3",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1564604963,
"version": "2.1.2",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1563957393,
"version": "2.1.1",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "2.1.0",
"changes": [
{
"note": "Add new assertions: `isArray`, `isBlockParam` and `isNumberOrBigNumber`",
"pr": 1823
},
{
"note": "Add `isNumberLike()` assertion",
"pr": 1819
}
],
"timestamp": 1563006338
},
{
"timestamp": 1557507213,
"version": "2.0.10",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "2.0.9",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1554997931
},
{
"timestamp": 1553183790,
"version": "2.0.8",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1553091633,
"version": "2.0.7",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1551479279,
"version": "2.0.6",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1551220833,
"version": "2.0.5",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1551130135,
"version": "2.0.4",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1549733923,
"version": "2.0.3",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "2.0.2",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1549547375
},
{
"timestamp": 1549452781,
"version": "2.0.1",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "2.0.0",
"changes": [
{
"note": "Upgrade the bignumber.js to v8.0.2",
"pr": 1517
}
],
"timestamp": 1549373905
},
{
"timestamp": 1547561734,
"version": "1.0.23",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1547225310,
"version": "1.0.22",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1547040760,
"version": "1.0.21",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "1.0.20",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1544739608
},
{
"version": "1.0.19",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1544570656
},
{
"timestamp": 1542821676,
"version": "1.0.18",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1542208198,
"version": "1.0.17",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1542028948,
"version": "1.0.16",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "1.0.15",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1541740904
},
{
"timestamp": 1539871071,
"version": "1.0.14",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "1.0.13",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1538693146
},
{
"timestamp": 1538157789,
"version": "1.0.12",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1537907159,
"version": "1.0.11",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1537875740,
"version": "1.0.10",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"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",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1535133899,
"version": "1.0.6",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1534210131,
"version": "1.0.5",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1532619515,
"version": "1.0.4",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1532614997,
"version": "1.0.3",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1532605697,
"version": "1.0.2",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1532357734,
"version": "1.0.1",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1532043000,
"version": "1.0.0",
"changes": [
{
"note": "Fix bug in string enum assertion. We erroneously were checking against the enum keys, not values",
"pr": 821
}
]
},
{
"timestamp": 1531919263,
"version": "0.2.14",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1531149657,
"version": "0.2.13",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1529397769,
"version": "0.2.12",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "0.2.11",
"changes": [
{
"note": "Incorrect publish that was unpublished"
}
],
"timestamp": 1527810075
},
{
"timestamp": 1527008270,
"version": "0.2.10",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1525477860,
"version": "0.2.9",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1525428773,
"version": "0.2.8",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1524044013,
"version": "0.2.7",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1523462196,
"version": "0.2.6",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1522673609,
"version": "0.2.5",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1522658513,
"version": "0.2.4",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "0.2.0",
"changes": [
{
"note": "Rename `isHttpUrl` to `isWebUri`",
"pr": 412
}
],
"timestamp": 1520434800
},
{
"version": "0.1.0",
"changes": [
{
"note": "Remove isETHAddressHex checksum address check and assume address will be lowercased ",
"pr": 373
},
{
"note": "Add an optional parameter `subSchemas` to `doesConformToSchema` method",
"pr": 385
}
],
"timestamp": 1520089200
},
{
"version": "0.0.18",
"changes": [
{
"note": "Fix publishing issue where .npmignore was not properly excluding undesired content",
"pr": 389
}
],
"timestamp": 1486566000
},
{
"version": "0.0.4",
"changes": [
{
"note": "Re-publish Assert previously published under NPM package @0xproject/0x-assert"
},
{
"note": "Added assertion isValidBaseUnitAmount which checks both that the value is a valid bigNumber and that it does not contain decimals."
}
],
"timestamp": 1510585200
}
]

View File

@ -1,293 +0,0 @@
<!--
changelogUtils.file is auto-generated using the monorepo-scripts package. Don't edit directly.
Edit the package's CHANGELOG.json file only.
-->
CHANGELOG
## v3.0.9 - _July 15, 2020_
* Dependencies updated
## v3.0.8 - _June 24, 2020_
* Dependencies updated
## v3.0.7 - _February 25, 2020_
* Dependencies updated
## v3.0.6 - _February 8, 2020_
* Dependencies updated
## v3.0.5 - _February 6, 2020_
* Dependencies updated
## v3.0.4 - _January 22, 2020_
* Dependencies updated
## v3.0.3 - _January 6, 2020_
* Dependencies updated
## v3.0.2 - _December 17, 2019_
* Dependencies updated
## v3.0.1 - _December 9, 2019_
* Dependencies updated
## v3.0.0 - _December 2, 2019_
* Dependencies updated
## v2.2.0-beta.3 - _December 2, 2019_
* Dependencies updated
## v2.2.0-beta.2 - _November 17, 2019_
* Dependencies updated
## v2.2.0-beta.1 - _November 7, 2019_
* Dependencies updated
## v2.2.0-beta.0 - _October 3, 2019_
* Dependencies updated
## v2.1.6 - _September 17, 2019_
* Dependencies updated
## v2.1.5 - _September 3, 2019_
* Dependencies updated
## v2.1.4 - _August 22, 2019_
* Dependencies updated
## v2.1.3 - _August 8, 2019_
* Dependencies updated
## v2.1.2 - _July 31, 2019_
* Dependencies updated
## v2.1.1 - _July 24, 2019_
* Dependencies updated
## v2.1.0 - _July 13, 2019_
* Add new assertions: `isArray`, `isBlockParam` and `isNumberOrBigNumber` (#1823)
* Add `isNumberLike()` assertion (#1819)
## v2.0.10 - _May 10, 2019_
* Dependencies updated
## v2.0.9 - _April 11, 2019_
* Dependencies updated
## v2.0.8 - _March 21, 2019_
* Dependencies updated
## v2.0.7 - _March 20, 2019_
* Dependencies updated
## v2.0.6 - _March 1, 2019_
* Dependencies updated
## v2.0.5 - _February 26, 2019_
* Dependencies updated
## v2.0.4 - _February 25, 2019_
* Dependencies updated
## v2.0.3 - _February 9, 2019_
* Dependencies updated
## v2.0.2 - _February 7, 2019_
* Dependencies updated
## v2.0.1 - _February 6, 2019_
* Dependencies updated
## v2.0.0 - _February 5, 2019_
* Upgrade the bignumber.js to v8.0.2 (#1517)
## v1.0.23 - _January 15, 2019_
* Dependencies updated
## v1.0.22 - _January 11, 2019_
* Dependencies updated
## v1.0.21 - _January 9, 2019_
* Dependencies updated
## v1.0.20 - _December 13, 2018_
* Dependencies updated
## v1.0.19 - _December 11, 2018_
* Dependencies updated
## v1.0.18 - _November 21, 2018_
* Dependencies updated
## v1.0.17 - _November 14, 2018_
* Dependencies updated
## v1.0.16 - _November 12, 2018_
* Dependencies updated
## v1.0.15 - _November 9, 2018_
* Dependencies updated
## v1.0.14 - _October 18, 2018_
* Dependencies updated
## v1.0.13 - _October 4, 2018_
* Dependencies updated
## v1.0.12 - _September 28, 2018_
* Dependencies updated
## v1.0.11 - _September 25, 2018_
* Dependencies updated
## v1.0.10 - _September 25, 2018_
* Dependencies updated
## v1.0.9 - _September 21, 2018_
* Dependencies updated
## v1.0.8 - _September 5, 2018_
* Dependencies updated
## v1.0.7 - _August 27, 2018_
* Dependencies updated
## v1.0.6 - _August 24, 2018_
* Dependencies updated
## v1.0.5 - _August 14, 2018_
* Dependencies updated
## v1.0.4 - _July 26, 2018_
* Dependencies updated
## v1.0.3 - _July 26, 2018_
* Dependencies updated
## v1.0.2 - _July 26, 2018_
* Dependencies updated
## v1.0.1 - _July 23, 2018_
* Dependencies updated
## v1.0.0 - _July 19, 2018_
* Fix bug in string enum assertion. We erroneously were checking against the enum keys, not values (#821)
## v0.2.14 - _July 18, 2018_
* Dependencies updated
## v0.2.13 - _July 9, 2018_
* Dependencies updated
## v0.2.12 - _June 19, 2018_
* Dependencies updated
## v0.2.11 - _May 31, 2018_
* Incorrect publish that was unpublished
## v0.2.10 - _May 22, 2018_
* Dependencies updated
## v0.2.9 - _May 4, 2018_
* Dependencies updated
## v0.2.8 - _May 4, 2018_
* Dependencies updated
## v0.2.7 - _April 18, 2018_
* Dependencies updated
## v0.2.6 - _April 11, 2018_
* Dependencies updated
## v0.2.5 - _April 2, 2018_
* Dependencies updated
## v0.2.4 - _April 2, 2018_
* Dependencies updated
## v0.2.0 - _March 7, 2018_
* Rename `isHttpUrl` to `isWebUri` (#412)
## v0.1.0 - _March 3, 2018_
* Remove isETHAddressHex checksum address check and assume address will be lowercased (#373)
* Add an optional parameter `subSchemas` to `doesConformToSchema` method (#385)
## v0.0.18 - _February 8, 2017_
* Fix publishing issue where .npmignore was not properly excluding undesired content (#389)
## v0.0.4 - _November 13, 2017_
* Re-publish Assert previously published under NPM package @0xproject/0x-assert
* Added assertion isValidBaseUnitAmount which checks both that the value is a valid bigNumber and that it does not contain decimals.

View File

@ -1,77 +0,0 @@
## @0x/assert
Standard type and schema assertions to be used across all 0x projects and packages
## Installation
```bash
yarn add @0x/assert
```
## Usage
```typescript
import { assert } from '@0x/assert';
assert.isValidBaseUnitAmount('baseUnitAmount', baseUnitAmount);
```
If your project is in [TypeScript](https://www.typescriptlang.org/), add the following to your `tsconfig.json`:
```json
"compilerOptions": {
"typeRoots": ["node_modules/@0x/typescript-typings/types", "node_modules/@types"],
}
```
## Contributing
We welcome improvements and fixes from the wider community! To report bugs within this package, please create an issue in this repository.
Please read our [contribution guidelines](../../CONTRIBUTING.md) before getting started.
### Install dependencies
If you don't have yarn workspaces enabled (Yarn < v1.0) - enable them:
```bash
yarn config set workspaces-experimental true
```
Then install dependencies
```bash
yarn install
```
### Build
To build this package and all other monorepo packages that it depends on, run the following from the monorepo root directory:
```bash
PKG=@0x/assert yarn build
```
Or continuously rebuild on change:
```bash
PKG=@0x/assert yarn watch
```
### Clean
```bash
yarn clean
```
### Lint
```bash
yarn lint
```
### Run Tests
```bash
yarn test
```

View File

@ -1,58 +0,0 @@
{
"name": "@0x/assert",
"version": "3.0.9",
"engines": {
"node": ">=6.12"
},
"description": "Provides a standard way of performing type and schema validation across 0x projects",
"main": "lib/src/index.js",
"types": "lib/src/index.d.ts",
"scripts": {
"build": "tsc -b",
"build:ci": "yarn build",
"clean": "shx rm -rf lib test_temp",
"lint": "tslint --format stylish --project .",
"fix": "tslint --fix --format stylish --project .",
"run_mocha": "mocha --require source-map-support/register --require make-promises-safe lib/test/**/*_test.js --exit",
"test": "yarn run_mocha",
"rebuild_and_test": "run-s clean build test",
"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"
},
"license": "Apache-2.0",
"repository": {
"type": "git",
"url": "https://github.com/0xProject/0x-monorepo.git"
},
"bugs": {
"url": "https://github.com/0xProject/0x-monorepo/issues"
},
"homepage": "https://github.com/0xProject/0x-monorepo/packages/assert/README.md",
"devDependencies": {
"@0x/tslint-config": "^4.1.0",
"@types/lodash": "4.14.104",
"@types/mocha": "^5.2.7",
"@types/valid-url": "^1.0.2",
"chai": "^4.0.1",
"dirty-chai": "^2.0.1",
"make-promises-safe": "^1.1.0",
"mocha": "^6.2.0",
"npm-run-all": "^4.1.2",
"nyc": "^11.0.1",
"shx": "^0.2.2",
"tslint": "5.11.0",
"typescript": "3.0.1"
},
"dependencies": {
"@0x/json-schemas": "^5.1.0",
"@0x/typescript-typings": "^5.1.1",
"@0x/utils": "^5.5.1",
"lodash": "^4.17.11",
"valid-url": "^1.0.9"
},
"publishConfig": {
"access": "public"
},
"gitHead": "4f91bfd907996b2f4dd383778b50c479c2602b56"
}

View File

@ -1,6 +0,0 @@
declare module '*.json' {
const json: any;
/* tslint:disable */
export default json;
/* tslint:enable */
}

View File

@ -1,127 +0,0 @@
import { Schema, SchemaValidator } from '@0x/json-schemas';
import { addressUtils, BigNumber, logUtils } from '@0x/utils';
import * as _ from 'lodash';
import * as validUrl from 'valid-url';
const HEX_REGEX = /^0x[0-9A-F]*$/i;
export const assert = {
isBigNumber(variableName: string, value: BigNumber): void {
const isBigNumber = BigNumber.isBigNumber(value);
assert.assert(isBigNumber, assert.typeAssertionMessage(variableName, 'BigNumber', value));
},
isNumberLike(variableName: string, value: BigNumber | number): void {
const isBigNumber = BigNumber.isBigNumber(value);
const isNumber = typeof value === 'number';
assert.assert(isBigNumber || isNumber, assert.typeAssertionMessage(variableName, 'BigNumber | number', value));
},
isValidBaseUnitAmount(variableName: string, value: BigNumber): void {
assert.isBigNumber(variableName, value);
const isNegative = value.isLessThan(0);
assert.assert(!isNegative, `${variableName} cannot be a negative number, found value: ${value.toNumber()}`);
const hasDecimals = value.decimalPlaces() !== 0;
assert.assert(
!hasDecimals,
`${variableName} should be in baseUnits (no decimals), found value: ${value.toNumber()}`,
);
},
isString(variableName: string, value: string): void {
assert.assert(_.isString(value), assert.typeAssertionMessage(variableName, 'string', value));
},
isFunction(variableName: string, value: any): void {
assert.assert(_.isFunction(value), assert.typeAssertionMessage(variableName, 'function', value));
},
isHexString(variableName: string, value: string): void {
assert.assert(
_.isString(value) && HEX_REGEX.test(value),
assert.typeAssertionMessage(variableName, 'HexString', value),
);
},
isETHAddressHex(variableName: string, value: string): void {
assert.assert(_.isString(value), assert.typeAssertionMessage(variableName, 'string', value));
assert.assert(addressUtils.isAddress(value), assert.typeAssertionMessage(variableName, 'ETHAddressHex', value));
},
doesBelongToStringEnum(
variableName: string,
value: string,
stringEnum: any /* There is no base type for every string enum */,
): void {
const enumValues = _.values(stringEnum);
const doesBelongToStringEnum = _.includes(enumValues, value);
const enumValuesAsStrings = _.map(enumValues, enumValue => `'${enumValue}'`);
const enumValuesAsString = enumValuesAsStrings.join(', ');
assert.assert(
doesBelongToStringEnum,
`Expected ${variableName} to be one of: ${enumValuesAsString}, encountered: ${value}`,
);
},
hasAtMostOneUniqueValue(value: any[], errMsg: string): void {
assert.assert(_.uniq(value).length <= 1, errMsg);
},
isNumber(variableName: string, value: number): void {
assert.assert(_.isFinite(value), assert.typeAssertionMessage(variableName, 'number', value));
},
isNumberOrBigNumber(variableName: string, value: any): void {
if (_.isFinite(value)) {
return;
} else {
assert.assert(
BigNumber.isBigNumber(value),
assert.typeAssertionMessage(variableName, 'number or BigNumber', value),
);
}
},
isBoolean(variableName: string, value: boolean): void {
assert.assert(_.isBoolean(value), assert.typeAssertionMessage(variableName, 'boolean', value));
},
isWeb3Provider(variableName: string, value: any): void {
logUtils.warn('DEPRECATED: Please use providerUtils.standardizeOrThrow() instead');
const isWeb3Provider = _.isFunction(value.send) || _.isFunction(value.sendAsync);
assert.assert(isWeb3Provider, assert.typeAssertionMessage(variableName, 'Provider', value));
},
doesConformToSchema(variableName: string, value: any, schema: Schema, subSchemas?: Schema[]): void {
if (value === undefined) {
throw new Error(`${variableName} can't be undefined`);
}
const schemaValidator = new SchemaValidator();
if (subSchemas !== undefined) {
_.map(subSchemas, schemaValidator.addSchema.bind(schemaValidator));
}
const validationResult = schemaValidator.validate(value, schema);
const hasValidationErrors = validationResult.errors.length > 0;
const msg = `Expected ${variableName} to conform to schema ${schema.id}
Encountered: ${JSON.stringify(value, null, '\t')}
Validation errors: ${validationResult.errors.join(', ')}`;
assert.assert(!hasValidationErrors, msg);
},
isWebUri(variableName: string, value: any): void {
const isValidUrl = validUrl.isWebUri(value) !== undefined;
assert.assert(isValidUrl, assert.typeAssertionMessage(variableName, 'web uri', value));
},
isUri(variableName: string, value: any): void {
const isValidUri = validUrl.isUri(value) !== undefined;
assert.assert(isValidUri, assert.typeAssertionMessage(variableName, 'uri', value));
},
isBlockParam(variableName: string, value: any): void {
if (Number.isInteger(value) && value >= 0) {
return;
}
if (value === 'earliest' || value === 'latest' || value === 'pending') {
return;
}
throw new Error(assert.typeAssertionMessage(variableName, 'BlockParam', value));
},
isArray(variableName: string, value: any): void {
if (!Array.isArray(value)) {
throw new Error(assert.typeAssertionMessage(variableName, 'Array', value));
}
},
assert(condition: boolean, message: string): void {
if (!condition) {
throw new Error(message);
}
},
typeAssertionMessage(variableName: string, type: string, value: any): string {
return `Expected ${variableName} to be of type ${type}, encountered: ${value}`;
},
};

View File

@ -1,265 +0,0 @@
import { schemas } from '@0x/json-schemas';
import { BigNumber } from '@0x/utils';
import * as chai from 'chai';
import * as dirtyChai from 'dirty-chai';
import 'mocha';
import { assert } from '../src/index';
chai.config.includeStack = true;
chai.use(dirtyChai);
const expect = chai.expect;
// tslint:disable:custom-no-magic-numbers
describe('Assertions', () => {
const variableName = 'variable';
describe('#isBigNumber', () => {
it('should not throw for valid input', () => {
const validInputs = [new BigNumber(23), new BigNumber('45')];
validInputs.forEach(input => expect(assert.isBigNumber.bind(assert, variableName, input)).to.not.throw());
});
it('should throw for invalid input', () => {
const invalidInputs = ['test', 42, false, { random: 'test' }, undefined];
invalidInputs.forEach(input => expect(assert.isBigNumber.bind(assert, variableName, input)).to.throw());
});
});
describe('#isNumberLike', () => {
it('should not throw for valid input', () => {
const validInputs = [new BigNumber(23), 23];
validInputs.forEach(input => expect(assert.isNumberLike.bind(assert, variableName, input)).to.not.throw());
});
it('should throw for invalid input', () => {
const invalidInputs = ['test', false, { random: 'test' }, undefined];
invalidInputs.forEach(input => expect(assert.isNumberLike.bind(assert, variableName, input)).to.throw());
});
});
describe('#isValidBaseUnitAmount', () => {
it('should not throw for valid input', () => {
const validInputs = [new BigNumber(23), new BigNumber('45000000')];
validInputs.forEach(input =>
expect(assert.isValidBaseUnitAmount.bind(assert, variableName, input)).to.not.throw(),
);
});
it('should throw for invalid input', () => {
const invalidInputs = [0, undefined, new BigNumber(3.145), 3.145, new BigNumber(-400)];
invalidInputs.forEach(input =>
expect(assert.isValidBaseUnitAmount.bind(assert, variableName, input)).to.throw(),
);
});
});
describe('#isString', () => {
it('should not throw for valid input', () => {
const validInputs = ['hello', 'goodbye'];
validInputs.forEach(input => expect(assert.isString.bind(assert, variableName, input)).to.not.throw());
});
it('should throw for invalid input', () => {
const invalidInputs = [42, false, { random: 'test' }, undefined, new BigNumber(45)];
invalidInputs.forEach(input => expect(assert.isString.bind(assert, variableName, input)).to.throw());
});
});
describe('#isFunction', () => {
it('should not throw for valid input', () => {
const validInputs = [BigNumber, assert.isString.bind(assert)];
validInputs.forEach(input => expect(assert.isFunction.bind(assert, variableName, input)).to.not.throw());
});
it('should throw for invalid input', () => {
const invalidInputs = [42, false, { random: 'test' }, undefined, new BigNumber(45)];
invalidInputs.forEach(input => expect(assert.isFunction.bind(assert, variableName, input)).to.throw());
});
});
describe('#isHexString', () => {
it('should not throw for valid input', () => {
const validInputs = [
'0x61a3ed31B43c8780e905a260a35faefEc527be7516aa11c0256729b5b351bc33',
'0x40349190569279751135161d22529dc25add4f6069af05be04cacbda2ace2254',
];
validInputs.forEach(input => expect(assert.isHexString.bind(assert, variableName, input)).to.not.throw());
});
it('should throw for invalid input', () => {
const invalidInputs = [
42,
false,
{ random: 'test' },
undefined,
new BigNumber(45),
'0x61a3ed31B43c8780e905a260a35faYfEc527be7516aa11c0256729b5b351bc33',
];
invalidInputs.forEach(input => expect(assert.isHexString.bind(assert, variableName, input)).to.throw());
});
});
describe('#isETHAddressHex', () => {
it('should not throw for valid input', () => {
const validInputs = [
'0x0000000000000000000000000000000000000000',
'0x6fffd0ae3f7d88c9b4925323f54c6e4b2918c5fd',
'0x12459c951127e0c374ff9105dda097662a027093',
];
validInputs.forEach(input =>
expect(assert.isETHAddressHex.bind(assert, variableName, input)).to.not.throw(),
);
});
it('should throw for invalid input', () => {
const invalidInputs = [
42,
false,
{ random: 'test' },
undefined,
new BigNumber(45),
'0x6FFFd0ae3f7d88c9b4925323f54c6e4b2918c5fd',
'0x6FFFd0ae3f7d88c9b4925323f54c6e4',
];
invalidInputs.forEach(input => expect(assert.isETHAddressHex.bind(assert, variableName, input)).to.throw());
});
});
describe('#doesBelongToStringEnum', () => {
enum TestEnums {
Test1 = 'Test1',
Test2 = 'Test2',
}
it('should not throw for valid input', () => {
const validInputs = [TestEnums.Test1, TestEnums.Test2];
validInputs.forEach(input =>
expect(assert.doesBelongToStringEnum.bind(assert, variableName, input, TestEnums)).to.not.throw(),
);
});
it('should throw for invalid input', () => {
const invalidInputs = [42, false, { random: 'test' }, undefined, new BigNumber(45)];
invalidInputs.forEach(input =>
expect(assert.doesBelongToStringEnum.bind(assert, variableName, input, TestEnums)).to.throw(),
);
});
});
describe('#hasAtMostOneUniqueValue', () => {
const errorMsg = 'more than one unique value';
it('should not throw for valid input', () => {
const validInputs = [['hello'], ['goodbye', 'goodbye', 'goodbye']];
validInputs.forEach(input =>
expect(assert.hasAtMostOneUniqueValue.bind(assert, input, errorMsg)).to.not.throw(),
);
});
it('should throw for invalid input', () => {
const invalidInputs = [['hello', 'goodbye'], ['goodbye', 42, false, false]];
invalidInputs.forEach(input =>
expect(assert.hasAtMostOneUniqueValue.bind(assert, input, errorMsg)).to.throw(),
);
});
});
describe('#isNumber', () => {
it('should not throw for valid input', () => {
const validInputs = [42, 0, 21e42];
validInputs.forEach(input => expect(assert.isNumber.bind(assert, variableName, input)).to.not.throw());
});
it('should throw for invalid input', () => {
const invalidInputs = [false, { random: 'test' }, undefined, new BigNumber(45)];
invalidInputs.forEach(input => expect(assert.isNumber.bind(assert, variableName, input)).to.throw());
});
});
describe('#isBoolean', () => {
it('should not throw for valid input', () => {
const validInputs = [true, false];
validInputs.forEach(input => expect(assert.isBoolean.bind(assert, variableName, input)).to.not.throw());
});
it('should throw for invalid input', () => {
const invalidInputs = [42, { random: 'test' }, undefined, new BigNumber(45)];
invalidInputs.forEach(input => expect(assert.isBoolean.bind(assert, variableName, input)).to.throw());
});
});
describe('#isWeb3Provider', () => {
it('should not throw for valid input', () => {
const validInputs = [{ send: () => 45 }, { sendAsync: () => 45 }];
validInputs.forEach(input =>
expect(assert.isWeb3Provider.bind(assert, variableName, input)).to.not.throw(),
);
});
it('should throw for invalid input', () => {
const invalidInputs = [42, { random: 'test' }, undefined, new BigNumber(45)];
invalidInputs.forEach(input => expect(assert.isWeb3Provider.bind(assert, variableName, input)).to.throw());
});
});
describe('#doesConformToSchema', () => {
const schema = schemas.addressSchema;
it('should not throw for valid input', () => {
const validInputs = [
'0x6fffd0ae3f7d88c9b4925323f54c6e4b2918c5fd',
'0x12459c951127e0c374ff9105dda097662a027093',
];
validInputs.forEach(input =>
expect(assert.doesConformToSchema.bind(assert, variableName, input, schema)).to.not.throw(),
);
});
it('should throw for invalid input', () => {
const invalidInputs = [42, { random: 'test' }, undefined, new BigNumber(45)];
invalidInputs.forEach(input =>
expect(assert.doesConformToSchema.bind(assert, variableName, input, schema)).to.throw(),
);
});
});
describe('#isWebUri', () => {
it('should not throw for valid input', () => {
const validInputs = [
'http://www.google.com',
'https://api.example-relayer.net',
'https://api.radarrelay.com/0x/v0/',
'https://zeroex.beta.radarrelay.com:8000/0x/v0/',
];
validInputs.forEach(input => expect(assert.isWebUri.bind(assert, variableName, input)).to.not.throw());
});
it('should throw for invalid input', () => {
const invalidInputs = [
42,
{ random: 'test' },
undefined,
new BigNumber(45),
'ws://www.api.example-relayer.net',
'www.google.com',
'api.example-relayer.net',
'user:password@api.example-relayer.net',
'//api.example-relayer.net',
];
invalidInputs.forEach(input => expect(assert.isWebUri.bind(assert, variableName, input)).to.throw());
});
});
describe('#isUri', () => {
it('should not throw for valid input', () => {
const validInputs = [
'http://www.google.com',
'https://api.example-relayer.net',
'https://api.radarrelay.com/0x/v0/',
'https://zeroex.beta.radarrelay.com:8000/0x/v0/',
'ws://www.api.example-relayer.net',
'wss://www.api.example-relayer.net',
'user:password@api.example-relayer.net',
];
validInputs.forEach(input => expect(assert.isUri.bind(assert, variableName, input)).to.not.throw());
});
it('should throw for invalid input', () => {
const invalidInputs = [
42,
{ random: 'test' },
undefined,
new BigNumber(45),
'www.google.com',
'api.example-relayer.net',
'//api.example-relayer.net',
];
invalidInputs.forEach(input => expect(assert.isUri.bind(assert, variableName, input)).to.throw());
});
});
describe('#assert', () => {
const assertMessage = 'assert not satisfied';
it('should not throw for valid input', () => {
expect(assert.assert.bind(assert, true, assertMessage)).to.not.throw();
});
it('should throw for invalid input', () => {
expect(assert.assert.bind(assert, false, assertMessage)).to.throw();
});
});
describe('#typeAssertionMessage', () => {
it('should render correct message', () => {
expect(assert.typeAssertionMessage('variable', 'string', 'number')).to.equal(
`Expected variable to be of type string, encountered: number`,
);
});
});
});
// tslint:enable:custom-no-magic-numbers

View File

@ -1,8 +0,0 @@
{
"extends": "../../tsconfig",
"compilerOptions": {
"outDir": "lib",
"rootDir": "."
},
"include": ["./src/**/*", "./test/**/*"]
}

View File

@ -1,3 +0,0 @@
{
"extends": ["@0x/tslint-config"]
}

View File

@ -1,10 +0,0 @@
# Blacklist all files
.*
*
# Whitelist lib
!lib/**/*
# Blacklist tests and publish scripts
/lib/test/*
/lib/monorepo_scripts/
# Package specific ignore

View File

@ -1,765 +0,0 @@
[
{
"timestamp": 1594788383,
"version": "6.2.3",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1592969527,
"version": "6.2.2",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1582623685,
"version": "6.2.1",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "6.2.0",
"changes": [
{
"note": "Ignore bytecode with unlinked library references in constructor",
"pr": 2463
},
{
"note": "Add exported function `linkLibrariesInBytecode()`",
"pr": 2463
}
],
"timestamp": 1581204851
},
{
"timestamp": 1580988106,
"version": "6.1.2",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "6.1.1",
"changes": [
{
"note": "Throw Error when revert is StringRevertError",
"pr": 2453
}
],
"timestamp": 1580811564
},
{
"version": "6.1.0",
"changes": [
{
"note": "Support catching empty reverts on live networks.",
"pr": 2433
}
],
"timestamp": 1579682890
},
{
"timestamp": 1578272714,
"version": "6.0.3",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1576540892,
"version": "6.0.2",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1575931811,
"version": "6.0.1",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "6.0.0",
"changes": [
{
"note": "Moved shared logic into `BaseContract` helpers to reduce size.",
"pr": 2343
},
{
"note": "Make `evmExecAsync` protected and rename to `_evmExecAsync`",
"pr": 2243
},
{
"note": "Remove duplicate types `IndexedFilterValues`, `DecodedLogEvent`, `EventCallback`",
"pr": 2243
},
{
"note": "Added ContractFunctionObj type and supporting types",
"pr": 2325
},
{
"note": "Added AwaitTransactionSuccessOpts and SendTransactionOpts",
"pr": 2325
},
{
"note": "Automatically decode and throw rich reverts in `_throwIfRevertWithReasonCallResult`",
"pr": 1761
},
{
"note": "Remove dependency on ethers.js",
"pr": 1761
},
{
"note": "Add more RevertError decoding functions",
"pr": 1819
},
{
"note": "Make the Promise returned by `awaitTransactionSuccessAsync` compatible with base Promise type",
"pr": 1885
},
{
"note": "Properly encode `BigNumber` indexed filter values in `getTopicsForIndexedArgs()`",
"pr": 2155
}
],
"timestamp": 1575296764
},
{
"version": "5.5.0-beta.4",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1575290197
},
{
"version": "5.5.0-beta.3",
"changes": [
{
"note": "Moved shared logic into `BaseContract` helpers to reduce size.",
"pr": 2343
}
],
"timestamp": 1574238768
},
{
"version": "5.5.0-beta.2",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1574030254
},
{
"version": "5.5.0-beta.1",
"changes": [
{
"note": "Make `evmExecAsync` protected and rename to `_evmExecAsync`",
"pr": 2243
},
{
"note": "Remove duplicate types `IndexedFilterValues`, `DecodedLogEvent`, `EventCallback`",
"pr": 2243
},
{
"note": "Added ContractFunctionObj type and supporting types",
"pr": 2325
},
{
"note": "Added AwaitTransactionSuccessOpts and SendTransactionOpts",
"pr": 2325
}
],
"timestamp": 1573159180
},
{
"version": "5.5.0-beta.0",
"changes": [
{
"note": "Automatically decode and throw rich reverts in `_throwIfRevertWithReasonCallResult`",
"pr": 1761
},
{
"note": "Remove dependency on ethers.js",
"pr": 1761
},
{
"note": "Add more RevertError decoding functions",
"pr": 1819
},
{
"note": "Make the Promise returned by `awaitTransactionSuccessAsync` compatible with base Promise type",
"pr": 1885
},
{
"note": "Properly encode `BigNumber` indexed filter values in `getTopicsForIndexedArgs()`",
"pr": 2155
}
],
"timestamp": 1570135330
},
{
"version": "5.4.0",
"changes": [
{
"note": "Add `evmExecAsync` to use local EVM instead of eth_call for pure functions",
"pr": 2108
}
],
"timestamp": 1568744790
},
{
"timestamp": 1567521715,
"version": "5.3.3",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "5.3.2",
"changes": [
{
"note": "Updated to ethereumjs-blockstream@^7.0.0",
"pr": 2089
}
],
"timestamp": 1566446343
},
{
"timestamp": 1565296576,
"version": "5.3.1",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "5.3.0",
"changes": [
{
"note": "Updated interface to `deployFrom0xArtifactAsync` to include log decode dependencies.",
"pr": 1995
},
{
"note": "Updated interface to `deployAsync` to include log decode dependencies.",
"pr": 1995
}
],
"timestamp": 1564604963
},
{
"version": "5.2.0",
"changes": [
{
"note": "Add SubscriptionManager",
"pr": 1970
}
]
},
{
"timestamp": 1563957393,
"version": "5.1.2",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1563006338,
"version": "5.1.1",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "5.1.0",
"changes": [
{
"note": "Export `PromiseWithTransactionHash` type",
"pr": 1797
}
],
"timestamp": 1557507213
},
{
"version": "5.0.5",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1554997931
},
{
"timestamp": 1553183790,
"version": "5.0.4",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1553091633,
"version": "5.0.3",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1551479279,
"version": "5.0.2",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1551220833,
"version": "5.0.1",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "5.0.0",
"changes": [
{
"note": "Add support for EIP1193 providers & Web3.js providers >= 1.0-beta.38",
"pr": 1627
},
{
"note": "Update provider params to type SupportedProvider which outlines all supported providers",
"pr": 1627
}
],
"timestamp": 1551130135
},
{
"timestamp": 1549733923,
"version": "4.0.3",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "4.0.2",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1549547375
},
{
"timestamp": 1549452781,
"version": "4.0.1",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "4.0.0",
"changes": [
{
"note": "Upgrade the bignumber.js to v8.0.2",
"pr": 1517
}
],
"timestamp": 1549373905
},
{
"timestamp": 1547561734,
"version": "3.0.13",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1547225310,
"version": "3.0.12",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1547040760,
"version": "3.0.11",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "3.0.10",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1544739608
},
{
"version": "3.0.9",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1544570656
},
{
"timestamp": 1543401373,
"version": "3.0.8",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1542821676,
"version": "3.0.7",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1542208198,
"version": "3.0.6",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1542134075,
"version": "3.0.5",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1542028948,
"version": "3.0.4",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "3.0.3",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1541740904
},
{
"timestamp": 1539871071,
"version": "3.0.2",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "3.0.1",
"changes": [
{
"note": "Dependencies updated"
}
],
"timestamp": 1538693146
},
{
"version": "3.0.0",
"changes": [
{
"note": "Change the way we detect BN to work with the newest ethers.js",
"pr": 1069
},
{
"note": "Add baseContract._throwIfRevertWithReasonCallResult",
"pr": 1069
}
],
"timestamp": 1538157789
},
{
"timestamp": 1537907159,
"version": "2.0.5",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1537875740,
"version": "2.0.4",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"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",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1535133899,
"version": "2.0.0",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "2.0.0-rc.1",
"changes": [
{
"pr": 915,
"note": "Added strict encoding/decoding checks for sendTransaction and call"
}
],
"timestamp": 1534210131
},
{
"timestamp": 1532619515,
"version": "1.0.4",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1532614997,
"version": "1.0.3",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1532605697,
"version": "1.0.2",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1532357734,
"version": "1.0.1",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1532043000,
"version": "1.0.0",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1531919263,
"version": "0.3.6",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1531149657,
"version": "0.3.5",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "0.3.4",
"changes": [
{
"note": "Update EthersJs to fix the `value.toLowerCase()` is not a function bug caused by `ethers.js` breaking patch version https://github.com/ethers-io/ethers.js/issues/201"
}
],
"timestamp": 1529397769
},
{
"timestamp": 1527810075,
"version": "0.3.3",
"changes": [
{
"note": "Incorrect publish that was unpublished"
}
]
},
{
"timestamp": 1527008270,
"version": "0.3.2",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"timestamp": 1525477860,
"version": "0.3.1",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "0.3.0",
"changes": [
{
"note": "Update ethers-contracts to ethers.js",
"pr": 540
}
],
"timestamp": 1525428773
},
{
"timestamp": 1524044013,
"version": "0.2.1",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "0.2.0",
"changes": [
{
"note": "Contract wrappers now accept Provider and defaults instead of Web3Wrapper",
"pr": 501
}
],
"timestamp": 1523462196
},
{
"version": "0.1.0",
"changes": [
{
"note": "Add tests for traversing ABI tree",
"pr": 485
},
{
"note": "Fix ABI tuples traversing",
"pr": 485
},
{
"note": "Fix ABI arrays traversing",
"pr": 485
}
],
"timestamp": 1522673609
},
{
"timestamp": 1522658513,
"version": "0.0.6",
"changes": [
{
"note": "Dependencies updated"
}
]
},
{
"version": "0.0.2",
"changes": [
{
"note": "Initial release"
}
],
"timestamp": 1520089200
}
]

View File

@ -1,320 +0,0 @@
<!--
changelogUtils.file is auto-generated using the monorepo-scripts package. Don't edit directly.
Edit the package's CHANGELOG.json file only.
-->
CHANGELOG
## v6.2.3 - _July 15, 2020_
* Dependencies updated
## v6.2.2 - _June 24, 2020_
* Dependencies updated
## v6.2.1 - _February 25, 2020_
* Dependencies updated
## v6.2.0 - _February 8, 2020_
* Ignore bytecode with unlinked library references in constructor (#2463)
* Add exported function `linkLibrariesInBytecode()` (#2463)
## v6.1.2 - _February 6, 2020_
* Dependencies updated
## v6.1.1 - _February 4, 2020_
* Throw Error when revert is StringRevertError (#2453)
## v6.1.0 - _January 22, 2020_
* Support catching empty reverts on live networks. (#2433)
## v6.0.3 - _January 6, 2020_
* Dependencies updated
## v6.0.2 - _December 17, 2019_
* Dependencies updated
## v6.0.1 - _December 9, 2019_
* Dependencies updated
## v6.0.0 - _December 2, 2019_
* Moved shared logic into `BaseContract` helpers to reduce size. (#2343)
* Make `evmExecAsync` protected and rename to `_evmExecAsync` (#2243)
* Remove duplicate types `IndexedFilterValues`, `DecodedLogEvent`, `EventCallback` (#2243)
* Added ContractFunctionObj type and supporting types (#2325)
* Added AwaitTransactionSuccessOpts and SendTransactionOpts (#2325)
* Automatically decode and throw rich reverts in `_throwIfRevertWithReasonCallResult` (#1761)
* Remove dependency on ethers.js (#1761)
* Add more RevertError decoding functions (#1819)
* Make the Promise returned by `awaitTransactionSuccessAsync` compatible with base Promise type (#1885)
* Properly encode `BigNumber` indexed filter values in `getTopicsForIndexedArgs()` (#2155)
## v5.5.0-beta.4 - _December 2, 2019_
* Dependencies updated
## v5.5.0-beta.3 - _November 20, 2019_
* Moved shared logic into `BaseContract` helpers to reduce size. (#2343)
## v5.5.0-beta.2 - _November 17, 2019_
* Dependencies updated
## v5.5.0-beta.1 - _November 7, 2019_
* Make `evmExecAsync` protected and rename to `_evmExecAsync` (#2243)
* Remove duplicate types `IndexedFilterValues`, `DecodedLogEvent`, `EventCallback` (#2243)
* Added ContractFunctionObj type and supporting types (#2325)
* Added AwaitTransactionSuccessOpts and SendTransactionOpts (#2325)
## v5.5.0-beta.0 - _October 3, 2019_
* Automatically decode and throw rich reverts in `_throwIfRevertWithReasonCallResult` (#1761)
* Remove dependency on ethers.js (#1761)
* Add more RevertError decoding functions (#1819)
* Make the Promise returned by `awaitTransactionSuccessAsync` compatible with base Promise type (#1885)
* Properly encode `BigNumber` indexed filter values in `getTopicsForIndexedArgs()` (#2155)
## v5.4.0 - _September 17, 2019_
* Add `evmExecAsync` to use local EVM instead of eth_call for pure functions (#2108)
## v5.3.3 - _September 3, 2019_
* Dependencies updated
## v5.3.2 - _August 22, 2019_
* Updated to ethereumjs-blockstream@^7.0.0 (#2089)
## v5.3.1 - _August 8, 2019_
* Dependencies updated
## v5.3.0 - _July 31, 2019_
* Updated interface to `deployFrom0xArtifactAsync` to include log decode dependencies. (#1995)
* Updated interface to `deployAsync` to include log decode dependencies. (#1995)
## v5.2.0 - _Invalid date_
* Add SubscriptionManager (#1970)
## v5.1.2 - _July 24, 2019_
* Dependencies updated
## v5.1.1 - _July 13, 2019_
* Dependencies updated
## v5.1.0 - _May 10, 2019_
* Export `PromiseWithTransactionHash` type (#1797)
## v5.0.5 - _April 11, 2019_
* Dependencies updated
## v5.0.4 - _March 21, 2019_
* Dependencies updated
## v5.0.3 - _March 20, 2019_
* Dependencies updated
## v5.0.2 - _March 1, 2019_
* Dependencies updated
## v5.0.1 - _February 26, 2019_
* Dependencies updated
## v5.0.0 - _February 25, 2019_
* Add support for EIP1193 providers & Web3.js providers >= 1.0-beta.38 (#1627)
* Update provider params to type SupportedProvider which outlines all supported providers (#1627)
## v4.0.3 - _February 9, 2019_
* Dependencies updated
## v4.0.2 - _February 7, 2019_
* Dependencies updated
## v4.0.1 - _February 6, 2019_
* Dependencies updated
## v4.0.0 - _February 5, 2019_
* Upgrade the bignumber.js to v8.0.2 (#1517)
## v3.0.13 - _January 15, 2019_
* Dependencies updated
## v3.0.12 - _January 11, 2019_
* Dependencies updated
## v3.0.11 - _January 9, 2019_
* Dependencies updated
## v3.0.10 - _December 13, 2018_
* Dependencies updated
## v3.0.9 - _December 11, 2018_
* Dependencies updated
## v3.0.8 - _November 28, 2018_
* Dependencies updated
## v3.0.7 - _November 21, 2018_
* Dependencies updated
## v3.0.6 - _November 14, 2018_
* Dependencies updated
## v3.0.5 - _November 13, 2018_
* Dependencies updated
## v3.0.4 - _November 12, 2018_
* Dependencies updated
## v3.0.3 - _November 9, 2018_
* Dependencies updated
## v3.0.2 - _October 18, 2018_
* Dependencies updated
## v3.0.1 - _October 4, 2018_
* Dependencies updated
## v3.0.0 - _September 28, 2018_
* Change the way we detect BN to work with the newest ethers.js (#1069)
* Add baseContract._throwIfRevertWithReasonCallResult (#1069)
## v2.0.5 - _September 25, 2018_
* Dependencies updated
## v2.0.4 - _September 25, 2018_
* Dependencies updated
## v2.0.3 - _September 21, 2018_
* Dependencies updated
## v2.0.2 - _September 5, 2018_
* Dependencies updated
## v2.0.1 - _August 27, 2018_
* Dependencies updated
## v2.0.0 - _August 24, 2018_
* Dependencies updated
## v2.0.0-rc.1 - _August 14, 2018_
* Added strict encoding/decoding checks for sendTransaction and call (#915)
## v1.0.4 - _July 26, 2018_
* Dependencies updated
## v1.0.3 - _July 26, 2018_
* Dependencies updated
## v1.0.2 - _July 26, 2018_
* Dependencies updated
## v1.0.1 - _July 23, 2018_
* Dependencies updated
## v1.0.0 - _July 19, 2018_
* Dependencies updated
## v0.3.6 - _July 18, 2018_
* Dependencies updated
## v0.3.5 - _July 9, 2018_
* Dependencies updated
## v0.3.4 - _June 19, 2018_
* Update EthersJs to fix the `value.toLowerCase()` is not a function bug caused by `ethers.js` breaking patch version https://github.com/ethers-io/ethers.js/issues/201
## v0.3.3 - _May 31, 2018_
* Incorrect publish that was unpublished
## v0.3.2 - _May 22, 2018_
* Dependencies updated
## v0.3.1 - _May 4, 2018_
* Dependencies updated
## v0.3.0 - _May 4, 2018_
* Update ethers-contracts to ethers.js (#540)
## v0.2.1 - _April 18, 2018_
* Dependencies updated
## v0.2.0 - _April 11, 2018_
* Contract wrappers now accept Provider and defaults instead of Web3Wrapper (#501)
## v0.1.0 - _April 2, 2018_
* Add tests for traversing ABI tree (#485)
* Fix ABI tuples traversing (#485)
* Fix ABI arrays traversing (#485)
## v0.0.6 - _April 2, 2018_
* Dependencies updated
## v0.0.2 - _March 3, 2018_
* Initial release

View File

@ -1,63 +0,0 @@
## @0x/base-contract
BaseContract to derive all auto-generated wrappers from
## Installation
```bash
yarn add @0x/base-contract
```
If your project is in [TypeScript](https://www.typescriptlang.org/), add the following to your `tsconfig.json`:
```json
"compilerOptions": {
"typeRoots": ["node_modules/@0x/typescript-typings/types", "node_modules/@types"],
}
```
## Usage
```javascript
import { BaseContract } from '@0x/base-contract';
```
## Contributing
We strongly recommend that the community help us make improvements and determine the future direction of the protocol. To report bugs within this package, please create an issue in this repository.
Please read our [contribution guidelines](../../CONTRIBUTING.md) before getting started.
### Install Dependencies
If you don't have yarn workspaces enabled (Yarn < v1.0) - enable them:
```bash
yarn config set workspaces-experimental true
```
Then install dependencies
```bash
yarn install
```
### Build
To build this package and all other monorepo packages that it depends on, run the following from the monorepo root directory:
```bash
PKG=@0x/base-contract yarn build
```
Or continuously rebuild on change:
```bash
PKG=@0x/base-contract yarn watch
```
### Lint
```bash
yarn lint
```

View File

@ -1,67 +0,0 @@
{
"name": "@0x/base-contract",
"version": "6.2.3",
"engines": {
"node": ">=6.12"
},
"description": "0x Base TS contract",
"main": "lib/src/index.js",
"types": "lib/src/index.d.ts",
"scripts": {
"build": "tsc -b",
"build:ci": "yarn build",
"clean": "shx rm -rf lib",
"test": "yarn run_mocha",
"rebuild_and_test": "run-s clean build test",
"test:circleci": "yarn test:coverage",
"run_mocha": "mocha --require source-map-support/register --require make-promises-safe lib/test/**/*_test.js --bail --exit",
"test:coverage": "nyc npm run test --all && yarn coverage:report:lcov",
"coverage:report:lcov": "nyc report --reporter=text-lcov > coverage/lcov.info",
"lint": "tslint --format stylish --project .",
"fix": "tslint --format stylish --fix --project ."
},
"license": "Apache-2.0",
"repository": {
"type": "git",
"url": "https://github.com/0xProject/0x-monorepo.git"
},
"bugs": {
"url": "https://github.com/0xProject/0x-monorepo/issues"
},
"homepage": "https://github.com/0xProject/0x-monorepo/packages/base-contract/README.md",
"devDependencies": {
"@0x/tslint-config": "^4.1.0",
"@0x/types": "^3.2.0",
"@0x/typescript-typings": "^5.1.1",
"@types/lodash": "4.14.104",
"@types/mocha": "^5.2.7",
"chai": "^4.0.1",
"ethereum-types": "^3.2.0",
"make-promises-safe": "^1.1.0",
"mocha": "^6.2.0",
"npm-run-all": "^4.1.2",
"shx": "^0.2.2",
"tslint": "5.11.0",
"typescript": "3.0.1"
},
"dependencies": {
"@0x/assert": "^3.0.9",
"@0x/json-schemas": "^5.1.0",
"@0x/utils": "^5.5.1",
"@0x/web3-wrapper": "^7.2.0",
"ethereumjs-account": "^3.0.0",
"ethereumjs-blockstream": "^7.0.0",
"ethereumjs-util": "^5.1.1",
"ethereumjs-vm": "^4.0.0",
"ethers": "~4.0.4",
"js-sha3": "^0.7.0",
"uuid": "^3.3.2"
},
"resolutions": {
"merkle-patricia-tree": "^2.3.2"
},
"publishConfig": {
"access": "public"
},
"gitHead": "4f91bfd907996b2f4dd383778b50c479c2602b56"
}

View File

@ -1,6 +0,0 @@
declare module '*.json' {
const json: any;
/* tslint:disable */
export default json;
/* tslint:enable */
}

View File

@ -1,405 +0,0 @@
import { assert } from '@0x/assert';
import { schemas } from '@0x/json-schemas';
import {
AbiEncoder,
abiUtils,
BigNumber,
decodeBytesAsRevertError,
decodeThrownErrorAsRevertError,
providerUtils,
RevertError,
StringRevertError,
} from '@0x/utils';
import { Web3Wrapper } from '@0x/web3-wrapper';
import {
AbiDefinition,
AbiType,
BlockParam,
CallData,
ConstructorAbi,
ContractAbi,
DataItem,
MethodAbi,
SupportedProvider,
TransactionReceiptWithDecodedLogs,
TxData,
TxDataPayable,
} from 'ethereum-types';
import Account from 'ethereumjs-account';
import * as util from 'ethereumjs-util';
import { default as VM } from 'ethereumjs-vm';
import PStateManager from 'ethereumjs-vm/dist/state/promisified';
export { linkLibrariesInBytecode, methodAbiToFunctionSignature } from './utils';
import { AwaitTransactionSuccessOpts } from './types';
import { formatABIDataItem } from './utils';
export { SubscriptionManager } from './subscription_manager';
export {
ContractEvent,
SendTransactionOpts,
AwaitTransactionSuccessOpts,
ContractFunctionObj,
ContractTxFunctionObj,
SubscriptionErrors,
} from './types';
export interface AbiEncoderByFunctionSignature {
[key: string]: AbiEncoder.Method;
}
const ARBITRARY_PRIVATE_KEY = 'e331b6d69882b4cb4ea581d88e0b604039a3de5967688d3dcffdd2270c0fd109';
// tslint:disable: max-classes-per-file
/**
* @dev A promise-compatible type that exposes a `txHash` field.
* Not used by BaseContract, but generated contracts will return it in
* `awaitTransactionSuccessAsync()`.
* Maybe there's a better place for this.
*/
export class PromiseWithTransactionHash<T> implements Promise<T> {
public readonly txHashPromise: Promise<string>;
private readonly _promise: Promise<T>;
constructor(txHashPromise: Promise<string>, promise: Promise<T>) {
this.txHashPromise = txHashPromise;
this._promise = promise;
}
// tslint:disable:promise-function-async
// tslint:disable:async-suffix
public then<TResult>(
onFulfilled?: (v: T) => TResult | Promise<TResult>,
onRejected?: (reason: any) => Promise<never>,
): Promise<TResult> {
return this._promise.then<TResult>(onFulfilled, onRejected);
}
public catch<TResult>(onRejected?: (reason: any) => Promise<TResult>): Promise<TResult | T> {
return this._promise.catch(onRejected);
}
public finally(onFinally?: (() => void) | null): Promise<T> {
return this._promise.finally(onFinally);
}
// tslint:enable:promise-function-async
// tslint:enable:async-suffix
get [Symbol.toStringTag](): 'Promise' {
return this._promise[Symbol.toStringTag];
}
}
export class BaseContract {
protected _abiEncoderByFunctionSignature: AbiEncoderByFunctionSignature;
protected _web3Wrapper: Web3Wrapper;
public abi: ContractAbi;
public address: string;
public contractName: string;
public constructorArgs: any[] = [];
public _deployedBytecodeIfExists?: Buffer;
private _evmIfExists?: VM;
private _evmAccountIfExists?: Buffer;
protected static _formatABIDataItemList(
abis: DataItem[],
values: any[],
formatter: (type: string, value: any) => any,
): any {
return values.map((value: any, i: number) => formatABIDataItem(abis[i], value, formatter));
}
protected static _lowercaseAddress(type: string, value: string): string {
return type === 'address' ? value.toLowerCase() : value;
}
protected static _bigNumberToString(_type: string, value: any): any {
return BigNumber.isBigNumber(value) ? value.toString() : value;
}
protected static _lookupConstructorAbi(abi: ContractAbi): ConstructorAbi {
const constructorAbiIfExists = abi.find(
(abiDefinition: AbiDefinition) => abiDefinition.type === AbiType.Constructor,
// tslint:disable-next-line:no-unnecessary-type-assertion
) as ConstructorAbi | undefined;
if (constructorAbiIfExists !== undefined) {
return constructorAbiIfExists;
} else {
// If the constructor is not explicitly defined, it won't be included in the ABI. It is
// still callable however, so we construct what the ABI would look like were it to exist.
const defaultConstructorAbi: ConstructorAbi = {
type: AbiType.Constructor,
stateMutability: 'nonpayable',
payable: false,
inputs: [],
};
return defaultConstructorAbi;
}
}
protected static _throwIfCallResultIsRevertError(rawCallResult: string): void {
// Try to decode the call result as a revert error.
let revert: RevertError;
try {
revert = decodeBytesAsRevertError(rawCallResult);
} catch (err) {
// Can't decode it as a revert error, so assume it didn't revert.
return;
}
throw revert;
}
protected static _throwIfThrownErrorIsRevertError(error: Error): void {
// Try to decode a thrown error.
let revertError: RevertError;
try {
revertError = decodeThrownErrorAsRevertError(error);
} catch (err) {
// Can't decode it.
return;
}
// Re-cast StringRevertErrors as plain Errors for backwards-compatibility.
if (revertError instanceof StringRevertError) {
throw new Error(revertError.values.message as string);
}
throw revertError;
}
protected static _throwIfUnexpectedEmptyCallResult(rawCallResult: string, methodAbi: AbiEncoder.Method): void {
// With live nodes, we will receive an empty call result if:
// 1. The function has no return value.
// 2. The contract reverts without data.
// 3. The contract reverts with an invalid opcode (`assert(false)` or `invalid()`).
if (!rawCallResult || rawCallResult === '0x') {
const returnValueDataItem = methodAbi.getReturnValueDataItem();
if (returnValueDataItem.components === undefined || returnValueDataItem.components.length === 0) {
// Expected no result (which makes it hard to tell if the call reverted).
return;
}
throw new Error(`Function "${methodAbi.getSignature()}" reverted with no data`);
}
}
// Throws if the given arguments cannot be safely/correctly encoded based on
// the given inputAbi. An argument may not be considered safely encodeable
// if it overflows the corresponding Solidity type, there is a bug in the
// encoder, or the encoder performs unsafe type coercion.
public static strictArgumentEncodingCheck(inputAbi: DataItem[], args: any[]): string {
const abiEncoder = AbiEncoder.create(inputAbi);
const params = abiUtils.parseEthersParams(inputAbi);
const rawEncoded = abiEncoder.encode(args);
const rawDecoded = abiEncoder.decodeAsArray(rawEncoded);
for (let i = 0; i < rawDecoded.length; i++) {
const original = args[i];
const decoded = rawDecoded[i];
if (!abiUtils.isAbiDataEqual(params.names[i], params.types[i], original, decoded)) {
throw new Error(
`Cannot safely encode argument: ${params.names[i]} (${original}) of type ${
params.types[i]
}. (Possible type overflow or other encoding error)`,
);
}
}
return rawEncoded;
}
protected static async _applyDefaultsToContractTxDataAsync<T extends Partial<TxData | TxDataPayable>>(
txData: T,
estimateGasAsync?: (txData: T) => Promise<number>,
): Promise<TxData> {
const txDataWithDefaults = BaseContract._removeUndefinedProperties<T>(txData);
if (txDataWithDefaults.gas === undefined && estimateGasAsync !== undefined) {
txDataWithDefaults.gas = await estimateGasAsync(txDataWithDefaults);
}
if (txDataWithDefaults.from !== undefined) {
txDataWithDefaults.from = txDataWithDefaults.from.toLowerCase();
}
return txDataWithDefaults as TxData;
}
protected static _assertCallParams(callData: Partial<CallData>, defaultBlock?: BlockParam): void {
assert.doesConformToSchema('callData', callData, schemas.callDataSchema, [
schemas.addressSchema,
schemas.numberSchema,
schemas.jsNumber,
]);
if (defaultBlock !== undefined) {
assert.isBlockParam('defaultBlock', defaultBlock);
}
}
private static _removeUndefinedProperties<T>(props: any): T {
const clonedProps = { ...props };
Object.keys(clonedProps).forEach(key => clonedProps[key] === undefined && delete clonedProps[key]);
return clonedProps;
}
protected _promiseWithTransactionHash(
txHashPromise: Promise<string>,
opts: AwaitTransactionSuccessOpts,
): PromiseWithTransactionHash<TransactionReceiptWithDecodedLogs> {
return new PromiseWithTransactionHash<TransactionReceiptWithDecodedLogs>(
txHashPromise,
(async (): Promise<TransactionReceiptWithDecodedLogs> => {
// When the transaction hash resolves, wait for it to be mined.
return this._web3Wrapper.awaitTransactionSuccessAsync(
await txHashPromise,
opts.pollingIntervalMs,
opts.timeoutMs,
);
})(),
);
}
protected async _applyDefaultsToTxDataAsync<T extends Partial<TxData | TxDataPayable>>(
txData: T,
estimateGasAsync?: (txData: T) => Promise<number>,
): Promise<TxData> {
// Gas amount sourced with the following priorities:
// 1. Optional param passed in to public method call
// 2. Global config passed in at library instantiation
// 3. Gas estimate calculation + safety margin
// tslint:disable-next-line:no-object-literal-type-assertion
const txDataWithDefaults = {
to: this.address,
...this._web3Wrapper.getContractDefaults(),
...BaseContract._removeUndefinedProperties(txData),
} as T;
if (txDataWithDefaults.gas === undefined && estimateGasAsync !== undefined) {
txDataWithDefaults.gas = await estimateGasAsync(txDataWithDefaults);
}
if (txDataWithDefaults.from !== undefined) {
txDataWithDefaults.from = txDataWithDefaults.from.toLowerCase();
}
return txDataWithDefaults as TxData;
}
protected async _evmExecAsync(encodedData: string): Promise<string> {
const encodedDataBytes = Buffer.from(encodedData.substr(2), 'hex');
const addressBuf = Buffer.from(this.address.substr(2), 'hex');
// should only run once, the first time it is called
if (this._evmIfExists === undefined) {
const vm = new VM({});
const psm = new PStateManager(vm.stateManager);
// create an account with 1 ETH
const accountPk = Buffer.from(ARBITRARY_PRIVATE_KEY, 'hex');
const accountAddress = util.privateToAddress(accountPk);
const account = new Account({ balance: 1e18 });
await psm.putAccount(accountAddress, account);
// 'deploy' the contract
if (this._deployedBytecodeIfExists === undefined) {
const contractCode = await this._web3Wrapper.getContractCodeAsync(this.address);
this._deployedBytecodeIfExists = Buffer.from(contractCode.substr(2), 'hex');
}
await psm.putContractCode(addressBuf, this._deployedBytecodeIfExists);
// save for later
this._evmIfExists = vm;
this._evmAccountIfExists = accountAddress;
}
let rawCallResult;
try {
const result = await this._evmIfExists.runCall({
to: addressBuf,
caller: this._evmAccountIfExists,
origin: this._evmAccountIfExists,
data: encodedDataBytes,
});
rawCallResult = `0x${result.execResult.returnValue.toString('hex')}`;
} catch (err) {
BaseContract._throwIfThrownErrorIsRevertError(err);
throw err;
}
BaseContract._throwIfCallResultIsRevertError(rawCallResult);
return rawCallResult;
}
protected async _performCallAsync(callData: Partial<CallData>, defaultBlock?: BlockParam): Promise<string> {
const callDataWithDefaults = await this._applyDefaultsToTxDataAsync(callData);
let rawCallResult: string;
try {
rawCallResult = await this._web3Wrapper.callAsync(callDataWithDefaults, defaultBlock);
} catch (err) {
BaseContract._throwIfThrownErrorIsRevertError(err);
throw err;
}
BaseContract._throwIfCallResultIsRevertError(rawCallResult);
return rawCallResult;
}
protected _lookupAbiEncoder(functionSignature: string): AbiEncoder.Method {
const abiEncoder = this._abiEncoderByFunctionSignature[functionSignature];
if (abiEncoder === undefined) {
throw new Error(`Failed to lookup method with function signature '${functionSignature}'`);
}
return abiEncoder;
}
protected _lookupAbi(functionSignature: string): MethodAbi {
const methodAbi = this.abi.find((abiDefinition: AbiDefinition) => {
if (abiDefinition.type !== AbiType.Function) {
return false;
}
// tslint:disable-next-line:no-unnecessary-type-assertion
const abiFunctionSignature = new AbiEncoder.Method(abiDefinition as MethodAbi).getSignature();
if (abiFunctionSignature === functionSignature) {
return true;
}
return false;
}) as MethodAbi;
return methodAbi;
}
protected _strictEncodeArguments(functionSignature: string, functionArguments: any): string {
const abiEncoder = this._lookupAbiEncoder(functionSignature);
const inputAbi = abiEncoder.getDataItem().components;
if (inputAbi === undefined) {
throw new Error(`Undefined Method Input ABI`);
}
const abiEncodedArguments = abiEncoder.encode(functionArguments);
return abiEncodedArguments;
}
/// @dev Constructs a contract wrapper.
/// @param contractName Name of contract.
/// @param abi of the contract.
/// @param address of the deployed contract.
/// @param supportedProvider for communicating with an ethereum node.
/// @param logDecodeDependencies the name and ABI of contracts whose event logs are
/// decoded by this wrapper.
/// @param deployedBytecode the deployedBytecode of the contract, used for executing
/// pure Solidity functions in memory. This is different from the bytecode.
constructor(
contractName: string,
abi: ContractAbi,
address: string,
supportedProvider: SupportedProvider,
callAndTxnDefaults?: Partial<CallData>,
logDecodeDependencies?: { [contractName: string]: ContractAbi },
deployedBytecode?: string,
) {
assert.isString('contractName', contractName);
assert.isETHAddressHex('address', address);
if (deployedBytecode !== undefined && deployedBytecode !== '') {
// `deployedBytecode` might contain references to
// unlinked libraries and, hence, would not be a hex string. We'll just
// leave `_deployedBytecodeIfExists` empty if this is the case.
// TODO(dorothy-zbornak): We should link the `deployedBytecode`
// beforehand in the generated wrappers.
try {
assert.isHexString('deployedBytecode', deployedBytecode);
this._deployedBytecodeIfExists = Buffer.from(deployedBytecode.substr(2), 'hex');
} catch (err) {
// Do nothing.
}
}
const provider = providerUtils.standardizeOrThrow(supportedProvider);
if (callAndTxnDefaults !== undefined) {
assert.doesConformToSchema('callAndTxnDefaults', callAndTxnDefaults, schemas.callDataSchema, [
schemas.addressSchema,
schemas.numberSchema,
schemas.jsNumber,
]);
}
this.contractName = contractName;
this._web3Wrapper = new Web3Wrapper(provider, callAndTxnDefaults);
this.abi = abi;
this.address = address;
const methodAbis = this.abi.filter(
(abiDefinition: AbiDefinition) => abiDefinition.type === AbiType.Function,
) as MethodAbi[];
this._abiEncoderByFunctionSignature = {};
methodAbis.forEach(methodAbi => {
const abiEncoder = new AbiEncoder.Method(methodAbi);
const functionSignature = abiEncoder.getSignature();
this._abiEncoderByFunctionSignature[functionSignature] = abiEncoder;
this._web3Wrapper.abiDecoder.addABI(abi, contractName);
});
if (logDecodeDependencies) {
Object.entries(logDecodeDependencies).forEach(([dependencyName, dependencyAbi]) =>
this._web3Wrapper.abiDecoder.addABI(dependencyAbi, dependencyName),
);
}
}
}

View File

@ -1,196 +0,0 @@
import { AbiDecoder, intervalUtils, logUtils } from '@0x/utils';
import { marshaller, Web3Wrapper } from '@0x/web3-wrapper';
import {
BlockParamLiteral,
BlockRange,
ContractAbi,
FilterObject,
LogEntry,
LogWithDecodedArgs,
RawLog,
RawLogEntry,
} from 'ethereum-types';
import { Block, BlockAndLogStreamer, Log } from 'ethereumjs-blockstream';
import { EventCallback, IndexedFilterValues } from '@0x/types';
import { SubscriptionErrors } from './types';
import { filterUtils } from './utils/filter_utils';
const DEFAULT_BLOCK_POLLING_INTERVAL = 1000;
export class SubscriptionManager<ContractEventArgs, ContractEvents extends string> {
public abi: ContractAbi;
private _blockAndLogStreamerIfExists: BlockAndLogStreamer<Block, Log> | undefined;
private _blockAndLogStreamIntervalIfExists?: NodeJS.Timer;
private readonly _web3Wrapper: Web3Wrapper;
private readonly _filters: { [filterToken: string]: FilterObject };
private readonly _filterCallbacks: {
[filterToken: string]: EventCallback<ContractEventArgs>;
};
private _onLogAddedSubscriptionToken: string | undefined;
private _onLogRemovedSubscriptionToken: string | undefined;
private static _onBlockAndLogStreamerError(isVerbose: boolean, err: Error): void {
// Since Blockstream errors are all recoverable, we simply log them if the verbose
// config is passed in.
if (isVerbose) {
logUtils.warn(err);
}
}
constructor(abi: ContractAbi, web3Wrapper: Web3Wrapper) {
this.abi = abi;
this._web3Wrapper = web3Wrapper;
this._filters = {};
this._filterCallbacks = {};
this._blockAndLogStreamerIfExists = undefined;
this._onLogAddedSubscriptionToken = undefined;
this._onLogRemovedSubscriptionToken = undefined;
}
public unsubscribeAll(): void {
const filterTokens = Object.keys(this._filterCallbacks);
filterTokens.forEach(filterToken => this.unsubscribe(filterToken));
}
public unsubscribe(filterToken: string, err?: Error): void {
if (this._filters[filterToken] === undefined) {
throw new Error(SubscriptionErrors.SubscriptionNotFound);
}
if (err !== undefined) {
const callback = this._filterCallbacks[filterToken];
callback(err, undefined);
}
delete this._filters[filterToken];
delete this._filterCallbacks[filterToken];
if (Object.keys(this._filters).length === 0) {
this._stopBlockAndLogStream();
}
}
public subscribe<ArgsType extends ContractEventArgs>(
address: string,
eventName: ContractEvents,
indexFilterValues: IndexedFilterValues,
abi: ContractAbi,
callback: EventCallback<ArgsType>,
isVerbose: boolean = false,
blockPollingIntervalMs?: number,
): string {
const filter = filterUtils.getFilter(address, eventName, indexFilterValues, abi);
if (this._blockAndLogStreamerIfExists === undefined) {
this._startBlockAndLogStream(isVerbose, blockPollingIntervalMs);
}
const filterToken = filterUtils.generateUUID();
this._filters[filterToken] = filter;
this._filterCallbacks[filterToken] = callback as EventCallback<ContractEventArgs>; // tslint:disable-line:no-unnecessary-type-assertion
return filterToken;
}
public async getLogsAsync<ArgsType extends ContractEventArgs>(
address: string,
eventName: ContractEvents,
blockRange: BlockRange,
indexFilterValues: IndexedFilterValues,
abi: ContractAbi,
): Promise<Array<LogWithDecodedArgs<ArgsType>>> {
const filter = filterUtils.getFilter(address, eventName, indexFilterValues, abi, blockRange);
const logs = await this._web3Wrapper.getLogsAsync(filter);
const logsWithDecodedArguments = logs.map(this._tryToDecodeLogOrNoop.bind(this)) as any[];
return logsWithDecodedArguments;
}
protected _tryToDecodeLogOrNoop<ArgsType extends ContractEventArgs>(
log: LogEntry,
): LogWithDecodedArgs<ArgsType> | RawLog {
const abiDecoder = new AbiDecoder([this.abi]);
const logWithDecodedArgs = abiDecoder.tryToDecodeLogOrNoop(log);
return logWithDecodedArgs;
}
private _onLogStateChanged<ArgsType extends ContractEventArgs>(
isRemoved: boolean,
blockHash: string,
rawLogs: RawLogEntry[],
): void {
const logs: LogEntry[] = rawLogs.map(rawLog => marshaller.unmarshalLog(rawLog));
logs.forEach(log => {
Object.entries(this._filters).forEach(([filterToken, filter]) => {
if (filterUtils.matchesFilter(log, filter)) {
const decodedLog = this._tryToDecodeLogOrNoop(log) as LogWithDecodedArgs<ArgsType>;
const logEvent = {
log: decodedLog,
isRemoved,
};
this._filterCallbacks[filterToken](null, logEvent);
}
});
});
}
private _startBlockAndLogStream(isVerbose: boolean, blockPollingIntervalMs?: number): void {
if (this._blockAndLogStreamerIfExists !== undefined) {
throw new Error(SubscriptionErrors.SubscriptionAlreadyPresent);
}
this._blockAndLogStreamerIfExists = new BlockAndLogStreamer(
this._blockstreamGetBlockOrNullAsync.bind(this),
this._blockstreamGetLogsAsync.bind(this),
SubscriptionManager._onBlockAndLogStreamerError.bind(this, isVerbose),
);
const catchAllLogFilter = {};
this._blockAndLogStreamerIfExists.addLogFilter(catchAllLogFilter);
const _blockPollingIntervalMs =
blockPollingIntervalMs === undefined ? DEFAULT_BLOCK_POLLING_INTERVAL : blockPollingIntervalMs;
this._blockAndLogStreamIntervalIfExists = intervalUtils.setAsyncExcludingInterval(
this._reconcileBlockAsync.bind(this),
_blockPollingIntervalMs,
SubscriptionManager._onBlockAndLogStreamerError.bind(this, isVerbose),
);
let isRemoved = false;
this._onLogAddedSubscriptionToken = this._blockAndLogStreamerIfExists.subscribeToOnLogsAdded(
this._onLogStateChanged.bind(this, isRemoved),
);
isRemoved = true;
this._onLogRemovedSubscriptionToken = this._blockAndLogStreamerIfExists.subscribeToOnLogsRemoved(
this._onLogStateChanged.bind(this, isRemoved),
);
}
// This method only exists in order to comply with the expected interface of Blockstream's constructor
private async _blockstreamGetBlockOrNullAsync(hash: string): Promise<Block | null> {
const shouldIncludeTransactionData = false;
const blockOrNull = await this._web3Wrapper.sendRawPayloadAsync<Block | null>({
method: 'eth_getBlockByHash',
params: [hash, shouldIncludeTransactionData],
});
return blockOrNull;
}
// This method only exists in order to comply with the expected interface of Blockstream's constructor
private async _blockstreamGetLatestBlockOrNullAsync(): Promise<Block | null> {
const shouldIncludeTransactionData = false;
const blockOrNull = await this._web3Wrapper.sendRawPayloadAsync<Block | null>({
method: 'eth_getBlockByNumber',
params: [BlockParamLiteral.Latest, shouldIncludeTransactionData],
});
return blockOrNull;
}
// This method only exists in order to comply with the expected interface of Blockstream's constructor
private async _blockstreamGetLogsAsync(filterOptions: FilterObject): Promise<RawLogEntry[]> {
const logs = await this._web3Wrapper.sendRawPayloadAsync<RawLogEntry[]>({
method: 'eth_getLogs',
params: [filterOptions],
});
return logs as RawLogEntry[];
}
private _stopBlockAndLogStream(): void {
if (this._blockAndLogStreamerIfExists === undefined) {
throw new Error(SubscriptionErrors.SubscriptionNotFound);
}
this._blockAndLogStreamerIfExists.unsubscribeFromOnLogsAdded(this._onLogAddedSubscriptionToken as string);
this._blockAndLogStreamerIfExists.unsubscribeFromOnLogsRemoved(this._onLogRemovedSubscriptionToken as string);
intervalUtils.clearAsyncExcludingInterval(this._blockAndLogStreamIntervalIfExists as NodeJS.Timer);
delete this._blockAndLogStreamerIfExists;
}
private async _reconcileBlockAsync(): Promise<void> {
const latestBlockOrNull = await this._blockstreamGetLatestBlockOrNullAsync();
if (latestBlockOrNull === null) {
return; // noop
}
// We need to coerce to Block type cause Web3.Block includes types for mempool blocks
if (this._blockAndLogStreamerIfExists !== undefined) {
// If we clear the interval while fetching the block - this._blockAndLogStreamer will be undefined
await this._blockAndLogStreamerIfExists.reconcileNewBlock(latestBlockOrNull);
}
}
}

View File

@ -1,55 +0,0 @@
import { BlockParam, CallData, LogEntryEvent, TransactionReceiptWithDecodedLogs, TxData } from 'ethereum-types';
import { PromiseWithTransactionHash } from './index';
export type LogEvent = LogEntryEvent;
export interface ContractEvent<ContractEventArgs> {
logIndex: number;
transactionIndex: number;
transactionHash: string;
blockHash: string;
blockNumber: number;
address: string;
type: string;
event: string;
args: ContractEventArgs;
}
export enum SubscriptionErrors {
SubscriptionNotFound = 'SUBSCRIPTION_NOT_FOUND',
SubscriptionAlreadyPresent = 'SUBSCRIPTION_ALREADY_PRESENT',
}
/**
* Used with `sendTransactionAsync`
* * shouldValidate: Flag indicating whether the library should make attempts to validate a transaction before
* broadcasting it. For example, order has a valid signature, maker has sufficient funds, etc. Default=true.
*/
export interface SendTransactionOpts {
shouldValidate?: boolean;
}
/**
* Used with `awaitTransactionSuccessAsync`
* * pollingIntervalMs: Determine polling intervals in milliseconds
* * timeoutMs: Determines timeout in milliseconds
*/
export interface AwaitTransactionSuccessOpts extends SendTransactionOpts {
pollingIntervalMs?: number;
timeoutMs?: number;
}
export interface ContractFunctionObj<T> {
callAsync(callData?: Partial<CallData>, defaultBlock?: BlockParam): Promise<T>;
getABIEncodedTransactionData(): string;
}
export interface ContractTxFunctionObj<T> extends ContractFunctionObj<T> {
sendTransactionAsync(txData?: Partial<TxData>, opts?: SendTransactionOpts): Promise<string>;
awaitTransactionSuccessAsync(
txData?: Partial<TxData>,
opts?: AwaitTransactionSuccessOpts,
): PromiseWithTransactionHash<TransactionReceiptWithDecodedLogs>;
estimateGasAsync(txData?: Partial<TxData>): Promise<number>;
}

View File

@ -1,72 +0,0 @@
import { AbiEncoder } from '@0x/utils';
import { ContractArtifact, DataItem, MethodAbi } from 'ethereum-types';
// tslint:disable-next-line:completed-docs
export function formatABIDataItem(abi: DataItem, value: any, formatter: (type: string, value: any) => any): any {
const trailingArrayRegex = /\[\d*\]$/;
if (abi.type.match(trailingArrayRegex)) {
const arrayItemType = abi.type.replace(trailingArrayRegex, '');
return value.map((val: any) => {
const arrayItemAbi = {
...abi,
type: arrayItemType,
};
return formatABIDataItem(arrayItemAbi, val, formatter);
});
} else if (abi.type === 'tuple') {
const formattedTuple: { [componentName: string]: DataItem } = {};
if (abi.components) {
abi.components.forEach(componentABI => {
formattedTuple[componentABI.name] = formatABIDataItem(
componentABI,
value[componentABI.name],
formatter,
);
});
}
return formattedTuple;
} else {
return formatter(abi.type, value);
}
}
/**
* Takes a MethodAbi and returns a function signature for ABI encoding/decoding
* @return a function signature as a string, e.g. 'functionName(uint256, bytes[])'
*/
export function methodAbiToFunctionSignature(methodAbi: MethodAbi): string {
const method = AbiEncoder.createMethod(methodAbi.name, methodAbi.inputs);
return method.getSignature();
}
/**
* Replaces unliked library references in the bytecode of a contract artifact
* with real addresses and returns the bytecode.
*/
export function linkLibrariesInBytecode(
artifact: ContractArtifact,
libraryAddresses: { [libraryName: string]: string },
): string {
const bytecodeArtifact = artifact.compilerOutput.evm.bytecode;
let bytecode = bytecodeArtifact.object.substr(2);
for (const link of Object.values(bytecodeArtifact.linkReferences)) {
for (const [libraryName, libraryRefs] of Object.entries(link)) {
const libraryAddress = libraryAddresses[libraryName];
if (!libraryAddress) {
throw new Error(
`${
artifact.contractName
} has an unlinked reference library ${libraryName} but no addresses was provided'.`,
);
}
for (const ref of libraryRefs) {
bytecode = [
bytecode.substring(0, ref.start * 2),
libraryAddress.toLowerCase().substr(2),
bytecode.substring((ref.start + ref.length) * 2),
].join('');
}
}
}
return `0x${bytecode}`;
}

View File

@ -1,93 +0,0 @@
import { IndexedFilterValues } from '@0x/types';
import { BigNumber } from '@0x/utils';
import { BlockRange, ContractAbi, EventAbi, FilterObject, LogEntry } from 'ethereum-types';
import * as ethUtil from 'ethereumjs-util';
import * as jsSHA3 from 'js-sha3';
import * as uuid from 'uuid/v4';
const TOPIC_LENGTH = 32;
export const filterUtils = {
generateUUID(): string {
return uuid();
},
getFilter<ContractEvents extends string>(
address: string,
eventName: ContractEvents,
indexFilterValues: IndexedFilterValues,
abi: ContractAbi,
blockRange?: BlockRange,
): FilterObject {
// tslint:disable:next-line no-unnecessary-type-assertion
const eventAbi = abi.find(abiDefinition => (abiDefinition as EventAbi).name === eventName) as EventAbi;
const eventSignature = filterUtils.getEventSignatureFromAbiByName(eventAbi);
const topicForEventSignature = ethUtil.addHexPrefix(jsSHA3.keccak256(eventSignature));
const topicsForIndexedArgs = filterUtils.getTopicsForIndexedArgs(eventAbi, indexFilterValues);
const topics = [topicForEventSignature, ...topicsForIndexedArgs];
let filter: FilterObject = {
address,
topics,
};
if (blockRange !== undefined) {
filter = {
...blockRange,
...filter,
};
}
return filter;
},
getEventSignatureFromAbiByName(eventAbi: EventAbi): string {
const types = eventAbi.inputs.map(i => i.type);
const signature = `${eventAbi.name}(${types.join(',')})`;
return signature;
},
getTopicsForIndexedArgs(abi: EventAbi, indexFilterValues: IndexedFilterValues): Array<string | null> {
const topics: Array<string | null> = [];
for (const eventInput of abi.inputs) {
if (!eventInput.indexed) {
continue;
}
if (indexFilterValues[eventInput.name] === undefined) {
// Null is a wildcard topic in a JSON-RPC call
topics.push(null);
} else {
// tslint:disable: no-unnecessary-type-assertion
let value = indexFilterValues[eventInput.name] as any;
if (BigNumber.isBigNumber(value)) {
// tslint:disable-next-line custom-no-magic-numbers
value = ethUtil.fromSigned(value.toString(10) as any);
}
// tslint:enable: no-unnecessary-type-assertion
const buffer = ethUtil.toBuffer(value);
const paddedBuffer = ethUtil.setLengthLeft(buffer, TOPIC_LENGTH);
const topic = ethUtil.bufferToHex(paddedBuffer);
topics.push(topic);
}
}
return topics;
},
matchesFilter(log: LogEntry, filter: FilterObject): boolean {
if (filter.address !== undefined && log.address !== filter.address) {
return false;
}
if (filter.topics !== undefined) {
return filterUtils.doesMatchTopics(log.topics, filter.topics);
}
return true;
},
doesMatchTopics(logTopics: string[], filterTopics: Array<string[] | string | null>): boolean {
const matchesTopic = logTopics.map((logTopic, i) => filterUtils.matchesTopic(logTopic, filterTopics[i]));
const doesMatchTopics = matchesTopic.every(m => m);
return doesMatchTopics;
},
matchesTopic(logTopic: string, filterTopic: string[] | string | null): boolean {
if (Array.isArray(filterTopic)) {
return filterTopic.includes(logTopic);
}
if (typeof filterTopic === 'string') {
return filterTopic === logTopic;
}
// null topic is a wildcard
return true;
},
};

View File

@ -1,114 +0,0 @@
import * as chai from 'chai';
import 'mocha';
import { BaseContract } from '../src';
const { expect } = chai;
describe('BaseContract', () => {
describe('strictArgumentEncodingCheck', () => {
it('works for simple types', () => {
BaseContract.strictArgumentEncodingCheck(
[{ name: 'to', type: 'address' }],
['0xe834ec434daba538cd1b9fe1582052b880bd7e63'],
);
});
it('works for array types', () => {
const inputAbi = [
{
name: 'takerAssetFillAmounts',
type: 'uint256[]',
},
];
const args = [
['9000000000000000000', '79000000000000000000', '979000000000000000000', '7979000000000000000000'],
];
BaseContract.strictArgumentEncodingCheck(inputAbi, args);
});
it('works for tuple/struct types', () => {
const inputAbi = [
{
components: [
{
name: 'makerAddress',
type: 'address',
},
{
name: 'takerAddress',
type: 'address',
},
{
name: 'feeRecipientAddress',
type: 'address',
},
{
name: 'senderAddress',
type: 'address',
},
{
name: 'makerAssetAmount',
type: 'uint256',
},
{
name: 'takerAssetAmount',
type: 'uint256',
},
{
name: 'makerFee',
type: 'uint256',
},
{
name: 'takerFee',
type: 'uint256',
},
{
name: 'expirationTimeSeconds',
type: 'uint256',
},
{
name: 'salt',
type: 'uint256',
},
{
name: 'makerAssetData',
type: 'bytes',
},
{
name: 'takerAssetData',
type: 'bytes',
},
],
name: 'order',
type: 'tuple',
},
];
const args = [
{
makerAddress: '0x6ecbe1db9ef729cbe972c83fb886247691fb6beb',
takerAddress: '0x0000000000000000000000000000000000000000',
feeRecipientAddress: '0xe834ec434daba538cd1b9fe1582052b880bd7e63',
senderAddress: '0x0000000000000000000000000000000000000000',
makerAssetAmount: '0',
takerAssetAmount: '200000000000000000000',
makerFee: '1000000000000000000',
takerFee: '1000000000000000000',
expirationTimeSeconds: '1532563026',
salt: '59342956082154660870994022243365949771115859664887449740907298019908621891376',
makerAssetData: '0xf47261b00000000000000000000000001dc4c1cefef38a777b15aa20260a54e584b16c48',
takerAssetData: '0xf47261b00000000000000000000000001d7022f5b17d2f8b695918fb48fa1089c9f85401',
},
];
BaseContract.strictArgumentEncodingCheck(inputAbi, args);
});
it('throws for integer overflows', () => {
expect(() =>
BaseContract.strictArgumentEncodingCheck([{ name: 'amount', type: 'uint8' }], ['256']),
).to.throw();
});
it('throws for fixed byte array overflows', () => {
expect(() =>
BaseContract.strictArgumentEncodingCheck([{ name: 'hash', type: 'bytes8' }], ['0x001122334455667788']),
).to.throw();
});
});
});

View File

@ -1,108 +0,0 @@
import { BigNumber } from '@0x/utils';
import * as chai from 'chai';
import 'mocha';
import { formatABIDataItem } from '../src/utils';
const { expect } = chai;
describe('Utils tests', () => {
describe('#formatABIDataItem', () => {
it('correctly handles arrays', () => {
const calls: Array<{ type: string; value: any }> = [];
const abi = {
name: 'values',
type: 'uint256[]',
};
const val = [1, 2, 3];
const formatted = formatABIDataItem(abi, val, (type: string, value: any) => {
calls.push({ type, value });
return value; // no-op
});
expect(formatted).to.be.deep.equal(val);
expect(calls).to.be.deep.equal([
{ type: 'uint256', value: 1 },
{ type: 'uint256', value: 2 },
{ type: 'uint256', value: 3 },
]);
});
it('correctly handles tuples', () => {
const calls: Array<{ type: string; value: any }> = [];
const abi = {
components: [
{
name: 'to',
type: 'address',
},
{
name: 'amount',
type: 'uint256',
},
],
name: 'data',
type: 'tuple',
};
const ZERO_ADDRESS = '0x0000000000000000000000000000000000000000';
const val = { to: ZERO_ADDRESS, amount: new BigNumber(1) };
const formatted = formatABIDataItem(abi, val, (type: string, value: any) => {
calls.push({ type, value });
return value; // no-op
});
expect(formatted).to.be.deep.equal(val);
expect(calls).to.be.deep.equal([
{
type: 'address',
value: val.to,
},
{
type: 'uint256',
value: val.amount,
},
]);
});
it('correctly handles nested arrays of tuples', () => {
const calls: Array<{ type: string; value: any }> = [];
const abi = {
components: [
{
name: 'to',
type: 'address',
},
{
name: 'amount',
type: 'uint256',
},
],
name: 'data',
type: 'tuple[2][]',
};
const ZERO_ADDRESS = '0x0000000000000000000000000000000000000000';
const val = [
[{ to: ZERO_ADDRESS, amount: new BigNumber(1) }, { to: ZERO_ADDRESS, amount: new BigNumber(2) }],
];
const formatted = formatABIDataItem(abi, val, (type: string, value: any) => {
calls.push({ type, value });
return value; // no-op
});
expect(formatted).to.be.deep.equal(val);
expect(calls).to.be.deep.equal([
{
type: 'address',
value: val[0][0].to,
},
{
type: 'uint256',
value: val[0][0].amount,
},
{
type: 'address',
value: val[0][1].to,
},
{
type: 'uint256',
value: val[0][1].amount,
},
]);
});
});
});

View File

@ -1,9 +0,0 @@
{
"extends": "../../tsconfig",
"compilerOptions": {
"outDir": "lib",
"rootDir": "."
},
"typeRoots": ["node_modules/@0x/typescript-typings/types", "node_modules/@types"],
"include": ["src/**/*", "test/**/*"]
}

View File

@ -1,3 +0,0 @@
{
"extends": ["@0x/tslint-config"]
}

Some files were not shown because too many files have changed in this diff Show More