Skip to content
This repository has been archived by the owner on Feb 26, 2024. It is now read-only.

v7.0.0

Compare
Choose a tag to compare
@MicaiahReid MicaiahReid released this 20 Jan 16:04
· 214 commits to master since this release
v7.0.0

 Highlights   Upgrade Guide and Breaking Changes   New Features   Changelog   Known Issues   Future Plans 


It's here, it's finally here! The much anticipated (well, at least by us!) Ganache v7 release has now been shipped! This release has been years in the making and we're really proud of the work we've done. We hope you love it as much as we do. If you do, or if you want to keep up with all things Ganache, be sure to give this repository a ⭐ star ⭐.


Thank you to everyone who has been a part of making this release happen — contributors, mentors, reviewers, issue reporters, and community participators have all been instrumental in making Ganache v7. We are immensely thankful to you all:

@davidmurdoch @MicaiahReid @gnidan @eggplantzzz @kevinweaver @cds-amal @haltman-at @kevinbluer @seesemichaelj @tcoulter @nicholasjpaterno @eshaben @CruzMolina @honestbonsai @domob1812 @moda20 @0xGorilla @fedgiac @FFdhorkin @NicsTr @convexman @rainwater11 @aliveli186 @winksaville @anvacaru @nepoche @gas1cent @Fatorin @0xng @wilwade @MatthiasLohr @alexhultman

As a token of our appreciation to our early contributors, we want to send you something real and tangible (sorry, no NFTs at this time 😔). Email [email protected] and we'll verify your identity to get it sent out to you (you'll just need to cover shipping if you're outside the United States). We want to keep it a little on the down-low to keep people from being jealous, but what we can tell you is that it's exclusive, brown, soft, wearable, with two arm holes (it's a t-shirt).


This is a huge release, so these release notes don't cover everything that's changed. For those gluttons for detail among us that want the comprehensive list, check out the notes from our alpha, beta, and rc releases:

Release Release Date
[email protected] 2021/08/26
[email protected] 2021/09/21
[email protected] 2021/11/12
[email protected] 2021/11/19
[email protected] 2021/11/24
[email protected] 2021/12/20
[email protected] 2022/01/12

For everyone else, we think these notes do a pretty great job of covering the features and changes that you'll care most about.


Highlights

Forking Got an Upgrade

Ganache's ancestor, Test RPC, was the first tool to introduce forking back in 2016. Ganache 7 takes forking to a new level.

Zero-Config Mainnet Forking

Truffle has partnered with Infura to provide free archive node access to Ganache users. Simply run ganache --fork and BOOM, you've forked mainnet at the latest block.

ganache --fork

But it doesn't stop there. Use ganache --fork NETWORK to fork the Ropsten, Kovan, Rinkeby and Görli networks.

SPPPPEEEEEEED

We've introduced two new caching layers that can reduce the run time of complex forking requests, like debug_traceTransaction, by over 30x!

In-memory LRU cache

The first caching layer is an in-memory LRU cache. This cache will store previous forking request results in memory so successive calls during the same Ganache session don't have to make the expensive network request to fetch the data again.

Persistent cache

The second caching layer is the more interesting cache and utilizes @truffle/db's network algorithm to efficiently store and retrieve requests and their responses to a persistent disk-backed database.

What this enables is for Ganache to differentiate blockchain networks based not on their chainId or networkId, but the contents of historical blocks.

You can always delete this persistent cache by running Ganache with the --fork.deleteCache flag. To disable both caches use the --fork.disableCache flag.

back to highlights

Ganache is Now Ganache

Before, the Ganache UI application was just Ganache, which used ganache-core, which was also used by ganache-cli. Confused? So were we. Which is why we thought a rename was in order.

Previously, ganache-core was the core code that powered the Ganache UI and Ganache CLI applications and allowed for programmatic use of Ganache. ganache-cli was a separate application that had to be installed to use Ganache in the command line.

We've now merged ganache-core and ganache-cli into just ganache. This one tool gives you access to Ganache as a command line application, for programmatic use in Node, or for use in the browser.

Note: In case you just love typing "-cli", we've left ganache-cli as an alias to ganache, so you can continue using the ganache-cli command in your npm scripts and in your terminal.

back to highlights

Use Ganache in the Browser

Why? We don't really know!

slack-conversation-release

But we're pretty sure you, our loyal and talented users, will make something great out of it. To use this feature, add the following script to your HTML:

<script src="https://cdn.jsdelivr.net/npm/ganache@{VERSION}/dist/web/ganache.min.js"></script>

NOTE: The {VERSION} in the above path needs to be replaced with a version number or tag that is listed in npm.

From there, Ganache is available in your browser for use:

const options = {};
const provider = Ganache.provider(options);

NOTE: Currently forking does not work in the browser, but we plan to add support in the future.

back to highlights

Huge Transaction Traces

If you've got transactions, we can trace 'em.™ Ganache can now run debug_traceTransaction on Ethereum's largest and most complex transactions, even those constrained by Node's runtime limitations!

We're proud of this one and will likely have a blog post coming soon to show off our JS-fu and explain how. For now, our past release notes go into some detail on this feature.

back to highlights

back to top


Upgrade Guide and Breaking Changes

In short, you can install the new version using:

npm install ganache --global

We've also written up this handy guide on how to upgrade/install Ganache and to document all breaking changes to look out for.

back to top


New Features


Berlin, London, and Arrow Glacier Hard Fork Support

Ganache now supports the Berlin, London, and Arrow Glacier hard forks. This means that EIP-2718's Typed Transaction Envelope, EIP-2930's Access List Transaction, and EIP-1559's Fee Market Transaction are all available for use in Ganache.

The default hard fork has been set to "london". Because of this, any legacy typed transactions (those with no "type" field) that don't supply a gas price, will automatically be upgraded to a "Type 2" EIP-1559 transaction.

back to new features

Future Nonces and Queued Transactions

Ganache now allows you to send what we call "future nonce transactions". These are transactions whose nonce is ahead of that of the sender's account. The transaction isn't immediately executable, so it stays in the transaction pool as a "queued" transaction.

Once the nonce gap is filled, the queued transaction will be executed automatically. For example, if a brand new account (nonce 0) sends transactions with nonces 1, 2, and 3, all three of these transactions will sit in the "queued" pool. As soon as a transaction from that account is sent with a nonce of 0, the nonce for the account is incremented to 1, so the transaction with nonce 1 is executed. At that point, the account's nonce is 2, so the transaction with nonce 2 is executed. Finally, the account's nonce is 3, so the transaction with account 3 is executed.

back to new features

Replacement Transactions

Replacement transactions are now supported in Ganache v7. This allows any transaction that is pending or queued in the transaction pool to be replaced by another transaction if the gas price of the new transaction is high enough compared to the original.

To send a replacement transaction, simply send a transaction with the same from and nonce fields as the transaction being replaced with a gas price that is --miner.priceBump (a configurable startup option, defaulted to 10%) higher than the original. Future nonce transactions that are queued up in the transaction pool are also able to be replaced.

back to new features

New RPC Endpoints

RPC methods provide access to Ethereum nodes and to Ganache. We've added some new methods to keep in step with real-world Ethereum nodes and some new custom methods to make your testing experience easier.

evm_setAccountNonce

This custom method allows you to (re)write history by setting an account's nonce.

evm_addAccount/evm_removeAccount

The evm_addAccount method can be used to add any address to the personal namespace. Ganache will create a fake private key which will then be used for all personal namespace commands sent using that added address. Here's an example of how to use this:

const zeroAddress = "0x0000000000000000000000000000000000000000"; // let's send transactions from the zero address!
const transaction = {from: zeroAddress};
const passphrase = "this is my passphrase";
// this will fail because we don't "know" the zero address
await assert.rejects(provider.send("personal_sendTransaction", [{ from: zeroAddress }, passphrase] ));

const added = await provider.send("evm_addAccount", [zeroAddress, passphrase] );
assert.equal(added, true) // but now we do!

// so now we can send transactions from the zero address!
const txHash = await provider.send("personal_sendTransaction", [{ from: zeroAddress }, passphrase] ))

The evm_removeAccount method can be used to do just the opposite — it will remove an account from the personal namespace.

eth_signTypedData_v4

We now support eth_signTypedData_v4, which can be used to sign typed data. For more information on this signing method, see MetaMask's helpful guide.

eth_maxPriorityFeePerGas

Ganache now supports the eth_maxPriorityFeePerGas RPC method. Currently, this defaults to returning 1 GWEI. In the future, we may adjust the behavior so it returns the current gas price minus the latest block's baseFeePerGas.

txpool_content

The new txpool_content RPC method returns the current contents of the transaction pool. The contents of the transaction pool are grouped into "pending" and "queued" transactions. "Pending" transactions are those that are immediately executable in the transaction pool, meaning that the transaction's nonce is equal to the sender account's next nonce. A "queued" transaction is one with a future nonce that is not immediately executable. Each of the groups of "pending" and "queued" transactions is grouped by the transaction's sender address, and a group of transactions from sender address are grouped by the sender address' nonce.

Here is an example response:

{
  "pending" : {
    "0x8e89f513c2ed8eb9d915196199615e590028b727" : {
      "0" : { /* eth_getTransactionByHash */ }
    }
  },
  "queued" : {
    "0x8e89f513c2ed8eb9d915196199615e590028b727" : {
      "2" : { ... },
      "3" : { ... },
    }
  }
}

back to new features

New Startup Options

Startup options are now grouped in the chain, database, fork, logging, miner, and wallet namespaces, and should be used as such on startup. For startup options in the CLI, use:

$ ganache --namespace.option="value"

and when using Ganache programmatically, you can do:

const options = { namespace: { option: "value"}};
const provider = ganache.provider(options);

We've also added to, updated, and renamed some startup options. To get a full list of options, you can always run ganache --help in the CLI, or you can check out our documentation. Here are the changes we've made in Ganache v7.

--miner.coinbase

The --miner.coinbase option allows you to set the address where mining rewards will go. By default, this is the zero address.

--miner.instamine

The --miner.instamine option allows you to configure when in the mining process Ganache returns a transaction's hash. This may sound trivial, but it can have some huge implications, which are covered in detail in this discussion.

In short, setting --miner.instamine="eager" (the default case), Ganache returns the transaction's hash to the caller after the transaction has been included in a block. This is the same as how Ganache v6 behaved, but differs from real nodes' behavior. Setting --miner.instamine="strict" works like a real node, the transaction's hash is returned before the transaction has been included in a block.

--miner.priceBump

The new --miner.priceBump option allows you to specify the percentage increase in the gas price required to replace an existing transaction. For example, if the price bump is set to 10% using --miner.priceBump=10 and a transaction with maxFeePerGas = 100 GWEI and maxPriorityFeePerGas = 1 GWEI is waiting in the transaction pool to be mined, a transaction with maxFeePerGas >= 110 GWEI and maxPriorityFeePerGas >= 1.1 GWEI will be required to replace the existing transaction.

--server.wsBinary

The --server.wsBinary option can now be used to set whether websockets should respond with binary data (ArrayBuffers) or strings. The default for this option is set to "auto", which responds with whichever type (binary data or string) you used in the request. Setting --server.wsBinary=true will always respond with binary data and --server.wsBinary=false will always respond with a string.

--wallet.lock

The --wallet.secure option has been renamed to --wallet.lock.

--wallet.passphrase

This feature allows you to specify a passphrase that will be used for personal namespace commands (personal_unlockAccount, personal_sendTransaction, etc.) on all startup accounts. Before this feature, the default (and only) password for startup accounts was "".

NOTE: Specifying the wallet.passphrase parameter does not lock accounts by default. The wallet.lock (previously wallet.secure) parameter can be used to lock accounts by default. If wallet.passphrase parameter is used without wallet.lock, the passphrase will still be used when personal_lockAccount is used.

back to new features

TypeScript Rewrite and Type Support

In this release Ganache has been almost completely rewritten from the ground up in TypeScript. With that, we are now exporting types in the published build, though it isn't perfect yet.

While Ganache is now a TypeScript project, all internal components are shipped in a bundle to improve installation time. While there are lots of tools to bundle JavaScript, the tools to bundle (or "rollup") these types aren't very mature and result in some strange types. We are now using ApiExtractor to generate our rollup types, as it works well for most of the types we need to export with one exception — it likes to rename types:

messed-up-types

EthereumProvider_2 in the above image should be EthereumProvider.

You find many other strangely named types in this version, as well as many types that aren't exported, but should be. We will have a fix out for this in the future.

back to new features

New Event System

In addition to EIP-1193's "message" event and the legacy "data" event, Ganache emits 3 additional events: "ganache:vm:tx:before", "ganache:vm:tx:step", and "ganache:vm:tx:after".

These events can be used to observe the lifecycle of any transaction executed via eth_sendTransaction, personal_sendTransaction, eth_sendRawTransaction, eth_call, debug_traceTransaction, or debug_storageRangeAt.

These share the event paradigm that Truffle uses, but without any of the wildcard handling, i.e., no "vm:*" support (for now).

Each of these events will emit a context object which is a unique object that can be used to identify a transaction over the course of its lifecycle. For example:

interface StepEvent {
  account: {
    nonce: bigint;
    balance: bigint;
    stateRoot: Buffer;
    codeHash: Buffer;
  };
  address: Buffer;
  codeAddress: Buffer;
  depth: number;
  gasLeft: bigint;
  gasRefund: bigint;
  memory: Buffer;
  memoryWordCount: bigint;
  opcode: {
    name: string;
    fee: number;
  };
  pc: number;
  returnStack: Buffer[];
  stack: Buffer[];
}
const contexts = new Map();
provider.on("ganache:vm:tx:before", (event: { context: {} }) => {
  contexts.set(event.context, []);
});
provider.on("ganache:vm:tx:step", (event: StepEvent) => {
  contexts.get(event.context).push(event.data);
});
provider.on("ganache:vm:tx:after", (event: { context: {} }) => {
  doAThingWithThisTransactionsSteps(contexts.get(event.context));
  contexts.delete(event.context);
});

The reason this context is necessary is that Ganache may run multiple transactions simultaneously, so "ganache:vm:tx:step" events from different transactions could be intermingled.

The above events will be emitted for eth_call, eth_sendTransaction, personal_sendTransaction, eth_sendRawTransaction, debug_traceTransaction, and debug_storageRangeAt.

Currently, we do not await the event listener's return value, however, we'll likely enable this in the future.

back to new features

Dropping Node 8 & 10, Adding Node 17

We are dropping support for Node.js versions 8 and 10 in the Ganache v7 release. This will simplify Ganache development and will result in smaller bundle sizes, as we no longer need to transpile features available natively in Node v12 for Node v10.

We've also added support for Node versions up to v17.

back to new features

back to top


Changelog

back to changelog

back to top


Known Issues

  • evm_setAccountNonce is race-conditiony (#1646)
  • --miner.callGasLimit implementation is wrong (#1645)
  • We don't return a proper pending block (#772)
  • Forking doesn't work in the browser (#1245)
  • Uncles aren't fully supported when forking (#786)
  • Forking may fail in weird and unexpected ways. We need to "error better" here (#615)
  • Node.js v12 outputs a µWS warning in the console (#2095)
  • Node.js v12 doesn't handle memory as well as 14+ and may crash computing very large debug_traceTransaction results (#2106)
  • Our bundle size is larger than ideal (#2096)

back to top


Future Plans

  • Update the eth_maxPriorityFeePerGas RPC method to return as Geth does, eth_gasPrice - baseFeePerGas (#2097)
  • Add support for the eth_feeHistory RPC method (#1470)
  • Support for enabling eligible draft EIPs before they are finalized or considered for inclusion in a hard fork (#1507)
  • New hard fork support well in advance of the hard fork launch (#2099)
  • Add an eth_createAccessList method (#1056)
  • Track test performance metrics over time (#2105)
  • Track real world Ganache usage (opt-in and anonymized) to better tune performance and drive bug fixes and feature development (#2100)
  • Track test coverage (#2101)
  • evm_mine will return the new blocks instead of just 0x0 (#536)
  • Add new evm_setCode and evm_setStorageAt RPC methods (#649)
  • Make evm_snapshot ids globally unique (unpredictable instead of a counter) (#655)
  • Support eth_getRawTransactionByHash RPC method (#135)
  • Support debug_accountAt RPC method (#813)
  • Allow "mining" to be disabled on start up (#248)
  • Set CLI options via config file, package.json, or ENV vars (#2102)
  • Create a CLI interactive/REPL mode (#2103)
  • Enable a CLI daemon mode (#2104)
  • "Flavor" Plugins: We're building support for Layer 2 plugins into Ganache so we can start up and manage other chains. e.g., The ganache filecoin command will look for the @ganache/filecoin package and start up a Filecoin and IPFS server.
  • Multi-chain configurations: you'll be able to start up your project's entire blockchain "ecosystem" from a single ganache command: e.g., ganache --flavor ethereum --flavor filecoin --flavor optimism.
    • this is where defining your CLI options via JSON config will come in very handy!
  • We've laid the groundwork for additional performance improvements. We expect to see an additional 2-5x speed up for typical testing work loads in the near future.

Open new issues (or join our team) to influence what we gets implemented and prioritized.

back to top


💖 The Truffle Team