* git rm unnecessary .gitkeep file * After all Pytest runs, show short test summary * abi-gen/Py: facilitate inlining of parameter lists Effectively, stopped new-lines from being introduced by calls to the `params` and `typed_params` partials. * abi-gen: simple Py wrapper test for local dev'ment * abi-gen/Py: stop gen'ing ValidatorBase * abi-gen/Py: declare abi() wrapper method in Base * abi-gen/Py: methods as classes to ease call/sendTx Represent methods as classes in order to faciliate access to a method's different operations (call, send_transaction, etc). * contract_wrappers.py: make Base methods public Changed some methods on BaseContractWrapper to be public. * contract_wrappers.py: remove unused method * contract_wrappers.py: extract method * abi-gen/Py: inline method * contract_wrappers.py: fix bug in call() We were passing transaction parameters through to sendTransaction() invocations, but not to call() invocations. * abi-gen/Py: remove `view_only` param to call/tx Formerly, in the BaseContractWrapper, there was just one function used for both eth_call and eth_sendTransaction, and you would distinguish between the two by specifying `view_only=True` when you wanted a call. This commit defines a method dedicated to executing an eth_call, and leaves the old method behind, with the `view_only` param removed, to be used for eth_sendTransaction. * abi-gen/Py: rename method * contract_wrappers/Py: simplify web3 func handling Pass web3 function instance into generated wrapper method class constructor, rather than having that class obtain it upon each method call. Really this is just an elimination of a call to BaseContractWrapper.contract_instance(), which will be removed completely in a shortly-upcoming commit. * contract_wrappers.py: inline method Inline and remove method BaseContractWrapper.contract_instance(). * contract_wrappers.py: pass Validator to *Method Pass a ValidatorBase instance into construction of the contract method classes, *Method, to eliminate another dependency on the containing contract object, which will be eliminated completely in a shortly-upcoming commit. * abi-gen/Py: BaseContractWrapper -> ContractMethod Change the fundamental thing-to-be-wrapped from the contract to the method. Since the named method classes were introduced (in a previous commit), and since the operations contained within the Base are predominantly focused on supporting method calls more than anything else, it makes more intuitive sense to provide a base for the methods than for the contract. With this change, the method classes no longer require a contract object to be passed to their constructors. The contract members that the methods were utilizing are now passed directly to the method constructor. * contract_wrappers.py: rename module to bases... ...from _base_contract_wrapper. The old name hasn't made sense since ValidatorBase was moved into that module, and definitely doesn't make sense now that the fundamental thing-to-be-wrapped has changed from the contract to the method. Also renamed to make it public (removed the leading underscore) since we're generating code that will depend on it. * abi-gen/Py: clarify call/sendTx docstrings * abi-gen/Py: adjust whitespace * contract_wrappers.py: inline method * abi-gen/Py: rename class ValidatorBase... ...to just Validator. It's in the "bases" module, which provides the context needed in order to know it's a base class * python-packages: fix silent failures of ./parallel * contract_wrappers.py: remove private_key support Having this present was overcomplicating interfaces. And it was untested (and not readily working when testing was attempted). And it only provided a thin layer of convenience, which a client could easily code up themselves. * contract_wrappers.py: inline method * contract_wrappers.py: rm unused member variables * contract_wrappers.py: rm unnecessary instance var * abi-gen/Py: add estimate_gas to gen'd methods * update CHANGELOG.json
ABI Gen
This package allows you to generate TypeScript contract wrappers from ABI files. It's heavily inspired by Geth abigen 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 are the templates used to generate the contract wrappers used by 0x.js.e
Installation
yarn add -g @0x/abi-gen
Usage
abi-gen
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. Either 'web3'
or 'ethers'. Ethers auto-converts small ints to numbers
whereas Web3 doesn't.
[string] [choices: "web3", "ethers"] [default: "web3"]
--network-id ID of the network where contract ABIs are nested in
artifacts [number] [default: 50]
You're required to pass a glob 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 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 and start adjusting them for your needs.
We use handlebars 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 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 of what we pass to the render method.
Output files
Output files will be generated within an output folder with names converted to camel case and taken from abi file names. If you already have some files in that folder they will be overwritten.
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 before getting started.
Install dependencies
If you don't have yarn workspaces enabled (Yarn < v1.0) - enable them:
yarn config set workspaces-experimental true
Then install dependencies
yarn install
Build
To build this package and all other monorepo packages that it depends on, run the following from the monorepo root directory:
PKG=@0x/abi-gen yarn build
Or continuously rebuild on change:
PKG=@0x/abi-gen yarn watch
Clean
yarn clean
Lint
yarn lint
CLI tests
The files in test-cli/ are used to test the CLI output against a set of dummy contracts.
Compile dummy contracts and generate wrappers:
yarn test_cli:prebuild
Build generated wrappers and 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}.