Pocket IC
We have released PocketIC server 4.0.0 and its Rust library 3.1.0.
IC HTTP interface compatibility
The most significant change in the new release is that PocketIC instances are now compatible with agent-based tools (agent.rs, agent.js, ic-repl, etc). Many existing dfx-based test suites can now be seamlessly integrated with PocketIC, and advanced tools such as ic-admin just work. You can even interact with frontend canisters running on PocketIC in your browser.
Note that PocketIC instances, if launched in the regular way, do not “make progress” by themselves, i.e., the state machines that represent subnets on the IC do not execute any messages without a call to tick()
and their timestamps lag behind the current time without a call to advance_time(...)
. But the agent-based tools expect their target to make progress automatically (as the IC mainnet and the replica launched by dfx do).
For that reason, you need to explicitly make an instance live by calling make_live(...)
on it. This will do three things:
- It launches a thread that calls
tick()
andadvance_time(...)
on the instance regularly - several times per second. - It creates a gateway (like icx-proxy for the replica launched by dfx) which points to this live instance.
- It returns a gateway URL which can then be passed to agent-like tools.
Attention: Enabling auto-progress makes instances non-deterministic! There is no way to guarantee message order when agents dispatch asynchronous requests, which may interleave with each other and with the tick
s from the auto-progress thread. If you need determinism, use the old, manually-tick
ed API.
Live instances can be made deterministic again by disabling auto-progress and disabling the gateway. This is done by calling make_deterministic
on the instance. Once this call returns, the instance will only continue to make progress when you call tick
- but the state in which the instance halts is not deterministic. So be extra careful with tests which are setup with a live phase and which then transition to non-live for the test section.
Caveat: Before you rush to migrate your tests from dfx + bash to PocketIC, be warned that HTTP outcalls, mainnet canister IDs for user-created canisters and Bitcoin integration are three features still missing in PocketIC.
For a minimal example, see HowTo.
Concurrent Update Calls
Another notable change in the new release are concurrent update calls.
Until the previous version, submitting ingress messages and executing them was tightly coupled in the method update_call
. Since version 4.0.0, the PocketIC server supports concurrent update calls, i.e., first submitting several messages that are later executed concurrently when awaited. This is useful for canister testing in the presence of interleaving update calls (e.g., ensuring that locking in critical sections works properly) and potentially also to speed up tests.
Calling the new method submit_call
on a PocketIC instance submits an update call for asynchronous execution and returns its message ID, without making any progress on this message. Later, the update call can be awaited by calling the method await_call
on the PocketIC instance passing the corresponding message ID as an argument. The method update_call
can be expressed in terms of the new methods like this:
let message_id = pic.submit_call(..., payload)?;
pic.await_call(message_id)
And the new methods enable interleaved use cases such as this:
let message_id_1 = pic.submit_call(..., payload_1)?;
let message_id_2 = pic.submit_call(..., payload_2)?;
pic.await_call(message_id_1);
pic.await_call(message_id_2);
Note that all update calls submitted for asynchronous execution are executed concurrently already when any one of them is being awaited using await_call
. This means that the update calls need not be awaited concurrently (as is the case for Rust futures that need to be awaited to even start executing). In particular, the second invocation of await_call
in the example above might return the result immediately without executing any additional rounds.
For more information, see HowTo.
For a complete list of changes, see the server changelog and the library changelog.
Your feedback helps us improve PocketIC, so please let us know your thoughts and questions in this thread.