feat: offchain reception#20893
Conversation
nventuro
left a comment
There was a problem hiding this comment.
Lovely. Left some comments but approving given that this is still in-progress work ultimtaely, no point in holding back the large changeset.
| }; | ||
|
|
||
| let offchain_inbox_sync_option = quote { | ||
| Option::some(aztec::messages::processing::offchain::sync_inbox) |
There was a problem hiding this comment.
So none would be disabling this feature, no?
There was a problem hiding this comment.
yes, maybe I grew too attached to the first implementation that used extensions
| ready_to_process | ||
| } | ||
|
|
||
| mod test { |
There was a problem hiding this comment.
With such long tests, you may want to consider putting these in a separate file (which would be processing/offchain/test.nr)
There was a problem hiding this comment.
will refactor later
noir-projects/aztec-nr/aztec/src/messages/processing/offchain.nr
Outdated
Show resolved
Hide resolved
|
|
||
| // QR payload is the offchain message for Bob. | ||
| const messageForBob = offchainMessages.find(msg => msg.recipient.equals(bob)); | ||
| expect(messageForBob).toBeTruthy(); |
There was a problem hiding this comment.
Should we leave a comment explaining the capsule issue?
|
❌ Failed to cherry-pick to |
Cherry-pick of b1ada99 with conflicts.
Cherry-pick of b1ada99 with conflicts.
Cherry-pick of b1ada99 onto v4-next. This commit contains conflict markers for reviewer visibility.
Cherry-pick of b1ada99 onto v4-next. This commit contains conflict markers for reviewer visibility.
Adds the ability to receive offchain messages to Aztec.nr contracts.
It works by using capsules to implement a persistent offchain message
inbox, and making sure that inbox is processed whenever `sync_state`
runs.
Apps deliver an offchain message to the inbox through a new utility
function `offchain_receive`, generated by the Aztec macro.
An `offchain::sync_inbox` function, takes the responsibility to let
`sync_state` know which messages should be processed like so:
1. Limits processed messages to those whose originating TX are available
at PXE's anchor block. To this end it uses a new
`resolve_message_contexts` oracle to determine which messages have
corresponding TXs known by PXE.
2. It is resilient to reorgs. Messages are re-processed for until
expiration time to make sure their effects don't get lost after re-orgs.
After expiration, they are safe to be discarded.
The feature can be exercised by invoking a function that emits offchain
messages on the sender side, saving the resulting offchain effects, and
then calling `offchain_receive` on the recipient side with them.
```typescript
// Alice sends the private transfer which emits offchain messages.
const { receipt, offchainMessages } = await contract.methods
.transfer_offchain(paymentAmount, bob)
.send({ from: alice });
expect(offchainMessages.length).toBeGreaterThan(0);
const messageForBob = offchainMessages.find(msg => msg.recipient.equals(bob));
expect(messageForBob).toBeTruthy();
await contract.methods
.offchain_receive([
{
ciphertext: messageForBob!.payload,
recipient: bob,
tx_hash: receipt.txHash.hash,
expiration_timestamp: messageForBob!.expirationTimestamp,
},
])
.simulate({ from: bob });
```
Known issues (can be addressed in subsequent PRs):
1. The new oracle, together with the long window offchain messages get
replayed for, means we should really cache `getTxEffects` node calls to
avoid performance regressions.
2. The current approach of PXE to caching contract sync calls, means
that with the current implementation we need to wait for one block
before a new message delivered to the inbox gets processed. We will
solve this by adding a new oracle to invalidate the contract sync cache.
3. Scopes aren't handled properly, which might need bigger refactors
that exceed offchain
Closes F-323
Closes F-327
Closes F-325
…ization race (#21452) ## Summary - Sets `anvilSlotsInAnEpoch: 32` in `e2e_offchain_payment` test setup, matching what `epochs_l1_reorgs` already does. ## Problem PR #21156 added `--slots-in-an-epoch 1` as the default for anvil, making `finalized = latest - 2`. PR #20893 added `e2e_offchain_payment` which simulates L1 reorgs. When both landed on `merge-train/fairies`, the reorg test fails deterministically because finalization races past the rollback target block. ## Fix Use `anvilSlotsInAnEpoch: 32` (matching Ethereum mainnet) so the finalized block stays far enough behind latest to allow rollbacks in the test. ClaudeBox log: https://claudebox.work/s/c5ac5d52da86e23a?run=4
BEGIN_COMMIT_OVERRIDE fix: skip oracle version check for pinned protocol contracts (#21349) fix: not reusing tags of partially reverted txs (#20817) feat: move storage_slot from partial commitment to completion hash (#21351) feat: offchain reception (#20893) fix: handle workspace members in needsRecompile crate collection (#21284) fix(aztec-nr): return Option from decode functions and fix event commitment capacity (#21264) fix: handle bad note lengths on compute_note_hash_and_nullifier (#21271) fix: address review feedback from PRs #21284 and #21237 (#21369) fix: claim contract & improve nullif docs (#21234) feat!: auto-enqueue public init nullifier for contracts with public functions (#20775) fix: search for all note nonces instead of just the one for the note index (#21438) fix: set anvilSlotsInAnEpoch in e2e_offchain_payment to prevent finalization race (#21452) fix: complete legacy oracle mappings for all pinned contracts (#21404) fix: correct inverted constrained encryption check in message delivery (#21399) feat!: improve L2ToL1MessageWitness API (#21231) END_COMMIT_OVERRIDE
Cherry-pick of b1ada99 onto v4-next. This commit contains conflict markers for reviewer visibility.
## Summary Backport of #20893 (feat: offchain reception) to `v4-next`. This adds offchain message reception to Aztec.nr contracts, including: - Persistent offchain message inbox via capsules - `offchain_receive` utility function auto-generated by the Aztec macro - `offchain::sync_inbox` for processing messages during `sync_state` - New `utilityResolveMessageContexts` oracle method - End-to-end test for offchain payments ## Backport details **Commit 1**: Raw cherry-pick with conflict markers (for reviewer visibility) **Commit 2**: Conflict resolution — kept v4-next's `utility`-prefixed oracle naming convention while integrating new offchain methods **Commit 3**: Updated `ORACLE_INTERFACE_HASH` for the new oracle method and bumped `ORACLE_VERSION` from 12 to 13 ### Conflicts resolved in: - `docs/netlify.toml` — added error code 7 redirect - `noir-projects/aztec-nr/aztec/src/macros/aztec.nr` — integrated `AztecConfig`, `#[varargs]`, offchain inbox sync - `noir-projects/aztec-nr/aztec/src/messages/discovery/mod.nr` — added offchain imports, kept v4-next's generic `Env` type - `noir-projects/aztec-nr/aztec/src/oracle/version.nr` — bumped to version 13 - `yarn-project/pxe/src/contract_function_simulator/oracle/interfaces.ts` — added `utilityResolveMessageContexts` - `yarn-project/pxe/src/contract_function_simulator/oracle/oracle.ts` — added oracle method - `yarn-project/pxe/src/contract_function_simulator/oracle/oracle_version_is_checked.test.ts` — added messageContextService mock - `yarn-project/pxe/src/contract_function_simulator/oracle/utility_execution_oracle.ts` — added implementation - `yarn-project/pxe/src/oracle_version.ts` — version 13, new hash - `yarn-project/txe/src/rpc_translator.ts` — added RPC translation ClaudeBox log: https://claudebox.work/s/f28700a7ecac0c5f?run=1 --------- Co-authored-by: Martin Verzilli <martin@aztec-labs.com>
…1414) (#21483) ## Summary Backport of #21414 to v4-next. Changes offchain messages to track anchor block timestamp for lifecycle management instead of transaction TTL. Adds `anchorBlockTimestamp` field to `OffchainMessage` type and passes it through all code paths that create offchain messages. ## Conflict Resolution Rebased onto latest `backport-to-v4-next-staging` (which now includes the offchain reception backport #20893). Only one conflict remained in `batch_call.test.ts` — accepted the new test cases from the original PR. ## Verification - yarn-project builds successfully - All unit tests pass (`interaction_options.test.ts`, `batch_call.test.ts`) ClaudeBox log: https://claudebox.work/s/f59343e7af96e770?run=2
Adds the ability to receive offchain messages to Aztec.nr contracts.
It works by using capsules to implement a persistent offchain message inbox, and making sure that inbox is processed whenever
sync_stateruns.Apps deliver an offchain message to the inbox through a new utility function
offchain_receive, generated by the Aztec macro.An
offchain::sync_inboxfunction, takes the responsibility to letsync_stateknow which messages should be processed like so:resolve_message_contextsoracle to determine which messages have corresponding TXs known by PXE.The feature can be exercised by invoking a function that emits offchain messages on the sender side, saving the resulting offchain effects, and then calling
offchain_receiveon the recipient side with them.Known issues (can be addressed in subsequent PRs):
getTxEffectsnode calls to avoid performance regressions.Closes F-323
Closes F-327
Closes F-325