Skip to content

Commit 9317322

Browse files
committed
feat: update to 3.0.0-devnet.20251212
1 parent 9dbe495 commit 9317322

File tree

11 files changed

+397
-350
lines changed

11 files changed

+397
-350
lines changed

.github/workflows/e2e.yml

Lines changed: 4 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -26,17 +26,15 @@ jobs:
2626
- name: Update path
2727
run: echo "/home/runner/.aztec/bin" >> $GITHUB_PATH
2828

29-
- name: Set Aztec version and start sandbox
29+
- name: Set Aztec version and start local network
3030
run: |
31-
aztec-up 3.0.0-devnet.4
32-
aztec start --sandbox &
31+
aztec-up 3.0.0-devnet.20251212
32+
aztec start --local-network &
3333
3434
- name: Install dependencies
35-
working-directory: ./app
36-
run: npm install -g yarn && yarn
35+
run: yarn install
3736

3837
- name: Install Playwright Browsers
39-
working-directory: ./app
4038
run: yarn playwright install --with-deps
4139

4240
- name: Build

APPLICATION_GUIDE.md

Lines changed: 29 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -107,10 +107,10 @@ A **nullifier** is a unique cryptographic value that:
107107
```typescript
108108
// From contracts/src/main.nr:48
109109
let nullifier = poseidon2_hash([
110-
context.msg_sender().unwrap().to_field(),
110+
self.msg_sender().unwrap().to_field(),
111111
secret,
112112
]);
113-
context.push_nullifier(nullifier);
113+
self.context.push_nullifier(nullifier);
114114
```
115115

116116
### 3. Sponsored Fee Payment
@@ -158,9 +158,9 @@ struct Storage<Context> {
158158

159159
```noir
160160
fn constructor(admin: AztecAddress) {
161-
storage.admin.write(admin);
162-
storage.vote_ended.write(false);
163-
storage.active_at_block.initialize(context.block_number());
161+
self.storage.admin.write(admin);
162+
self.storage.vote_ended.write(false);
163+
self.storage.active_at_block.initialize(self.context.block_number());
164164
}
165165
```
166166

@@ -171,17 +171,17 @@ fn constructor(admin: AztecAddress) {
171171
fn cast_vote(candidate: Field) {
172172
// Step 1: Get nullifier public key
173173
let msg_sender_nullifier_public_key_message_hash =
174-
get_public_keys(context.msg_sender().unwrap()).npk_m.hash();
174+
get_public_keys(self.msg_sender().unwrap()).npk_m.hash();
175175
176176
// Step 2: Get secret key (only you can do this)
177-
let secret = context.request_nsk_app(msg_sender_nullifier_public_key_message_hash);
177+
let secret = self.context.request_nsk_app(msg_sender_nullifier_public_key_message_hash);
178178
179179
// Step 3: Create nullifier (prevents double voting)
180-
let nullifier = poseidon2_hash([context.msg_sender().unwrap().to_field(), secret]);
181-
context.push_nullifier(nullifier);
180+
let nullifier = poseidon2_hash([self.msg_sender().unwrap().to_field(), secret]);
181+
self.context.push_nullifier(nullifier);
182182
183-
// Step 4: Add vote to public tally (in a separate public function)
184-
PrivateVoting::at(context.this_address()).add_to_tally_public(candidate).enqueue(&mut context);
183+
// Step 4: Add vote to public tally (using enqueue_self for same-contract calls)
184+
self.enqueue_self.add_to_tally_public(candidate);
185185
}
186186
```
187187

@@ -194,21 +194,21 @@ fn cast_vote(candidate: Field) {
194194
**add_to_tally_public** - Public function to increment vote count
195195

196196
```noir
197+
#[only_self]
197198
#[external("public")]
198-
#[internal]
199199
fn add_to_tally_public(candidate: Field) {
200-
assert(storage.vote_ended.read() == false, "Vote has ended");
201-
let new_tally = storage.tally.at(candidate).read() + 1;
202-
storage.tally.at(candidate).write(new_tally);
200+
assert(self.storage.vote_ended.read() == false, "Vote has ended");
201+
let new_tally = self.storage.tally.at(candidate).read() + 1;
202+
self.storage.tally.at(candidate).write(new_tally);
203203
}
204204
```
205205

206206
**get_vote** - Read vote tally (unconstrained = free to call)
207207

208208
```noir
209209
#[external("utility")]
210-
unconstrained fn get_vote(candidate: Field) -> Field {
211-
storage.tally.at(candidate).read()
210+
unconstrained fn get_vote(candidate: Field) -> pub Field {
211+
self.storage.tally.at(candidate).read()
212212
}
213213
```
214214

@@ -390,8 +390,8 @@ voteButton.addEventListener('click', async (e) => {
390390
throw new Error('No account connected');
391391
}
392392

393-
// 3. Prepare contract interaction
394-
const votingContract = await PrivateVotingContract.at(
393+
// 3. Prepare contract interaction (Contract.at is now synchronous)
394+
const votingContract = PrivateVotingContract.at(
395395
AztecAddress.fromString(contractAddress),
396396
wallet
397397
);
@@ -411,7 +411,7 @@ voteButton.addEventListener('click', async (e) => {
411411

412412
```typescript
413413
async function updateVoteTally(wallet: Wallet, from: AztecAddress) {
414-
const votingContract = await PrivateVotingContract.at(
414+
const votingContract = PrivateVotingContract.at(
415415
AztecAddress.fromString(contractAddress),
416416
wallet
417417
);
@@ -572,10 +572,10 @@ stateDiagram-v2
572572
- State is transparent
573573
- Example: `add_to_tally_public()`
574574

575-
**Internal Functions** (`#[internal]`):
575+
**Only-Self Functions** (`#[only_self]`):
576576

577-
- Can only be called from within the contract
578-
- Example: `add_to_tally_public()` is internal and can only be called by `cast_vote()`
577+
- Can only be called from within the same contract
578+
- Example: `add_to_tally_public()` can only be called by `cast_vote()` via `self.enqueue_self`
579579

580580
**Utility Functions** (`#[external("utility")]`):
581581

@@ -612,8 +612,8 @@ The `cast_vote` function uses a clever pattern:
612612
**Prerequisites**:
613613

614614
```bash
615-
# Install Aztec tools (version 3.0.0-devnet.4)
616-
aztec-up 3.0.0-devnet.4
615+
# Install Aztec tools (version 3.0.0-devnet.20251212)
616+
aztec-up 3.0.0-devnet.20251212
617617

618618
# Install dependencies
619619
yarn install
@@ -627,10 +627,9 @@ yarn build-contracts
627627

628628
What happens:
629629

630-
1. Noir compiler (`aztec-nargo`) compiles `contracts/src/main.nr`
631-
2. Post-processor generates artifacts
632-
3. TypeScript bindings are generated
633-
4. Artifacts copied to `app/artifacts/`
630+
1. Aztec CLI (`aztec compile`) compiles `contracts/src/main.nr`
631+
2. TypeScript bindings are generated (`aztec codegen`)
632+
3. Artifacts copied to `app/artifacts/`
634633

635634
**Step 2: Deploy Contracts**
636635

@@ -740,4 +739,4 @@ PROVER_ENABLED=true # Enable/disable proving
740739

741740
---
742741

743-
_Generated for aztec-web-starter - Aztec 3.0.0-devnet.4_
742+
_Generated for aztec-web-starter - Aztec 3.0.0-devnet.20251212_

README.md

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -4,15 +4,15 @@ This is an example web app that demonstrates how to interact with an Aztec contr
44

55
- Uses the [Private Voting](https://docs.aztec.network/developers/tutorials/codealong/contract_tutorials/private_voting_contract) example
66
- Includes an embedded wallet. This is only for demonstration purposes and not for production use.
7-
- Works on top of the Sandbox, but can be adapted to work with a testnet.
7+
- Works on top of the local network, but can be adapted to work with a testnet.
88

99
### Setup
1010

1111
1. Install the Aztec tools from the first few steps in [Quick Start Guide](https://docs.aztec.network/developers/getting_started).
1212

13-
Please note that this project uses `3.0.0-devnet.4` version of Aztec SDK. If you wish to use a different version, please update the dependencies in the `app/package.json` and in `contracts/Nargo.toml` file to match your version.
13+
Please note that this project uses `3.0.0-devnet.20251212` version of Aztec SDK. If you wish to use a different version, please update the dependencies in the `package.json` and in `contracts/Nargo.toml` file to match your version.
1414

15-
You can install a specific version of Aztec tools by running `aztec-up 3.0.0-devnet.4`
15+
You can install a specific version of Aztec tools by running `aztec-up 3.0.0-devnet.20251212`
1616

1717
2. Compile smart contracts in `/contracts`:
1818

@@ -31,11 +31,11 @@ yarn install
3131
yarn deploy-contracts
3232
```
3333

34-
The deploy script generates a random account and deploys the voting contract with it. It also uses the SponsoredFPC contract for fee payment. This is sufficient for testing with Sandbox, but is not suitable for production setup.
34+
The deploy script generates a random account and deploys the voting contract with it. It also uses the SponsoredFPC contract for fee payment. This is sufficient for testing with local network, but is not suitable for production setup.
3535

3636
The script also writes the deployment info to `.env` (which our web-app reads from).
3737

38-
> Note that the script generates client proofs and it may take a couple of seconds. For faster development, you can disable proving by calling with `PROVER_ENABLED=false` (Sandbox accepts transactions without a valid proof).
38+
> Note that the script generates client proofs and it may take a couple of seconds. For faster development, you can disable proving by calling with `PROVER_ENABLED=false` (The local network accepts transactions without a valid proof).
3939
4040
4. Run the app (development mode):
4141

@@ -65,7 +65,7 @@ yarn test
6565

6666
## Disable client proofs
6767

68-
The Sandbox will accept transactions without a valid proof. You can disable proof generation when working against the Sandbox as it will save time during development.
68+
The local network will accept transactions without a valid proof. You can disable proof generation when working against the local network as it will save time during development.
6969

7070
To disable proving in the deploy script, run:
7171

app/embedded-wallet.ts

Lines changed: 37 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -1,13 +1,20 @@
11
import { Account, SignerlessAccount } from '@aztec/aztec.js/account';
2-
import { AztecAddress } from '@aztec/aztec.js/addresses';
32
import { getContractInstanceFromInstantiationParams } from '@aztec/aztec.js/contracts';
43
import { SponsoredFeePaymentMethod } from '@aztec/aztec.js/fee';
5-
import { Fr } from '@aztec/aztec.js/fields';
64
import { createLogger } from '@aztec/aztec.js/log';
75
import { createAztecNodeClient } from '@aztec/aztec.js/node';
8-
import { type UserFeeOptions, type FeeOptions, BaseWallet, AccountManager, DeployAccountOptions, SimulateOptions } from '@aztec/aztec.js/wallet';
6+
import {
7+
AccountManager,
8+
type DeployAccountOptions,
9+
type SimulateOptions,
10+
} from '@aztec/aztec.js/wallet';
911
import { SPONSORED_FPC_SALT } from '@aztec/constants';
10-
import { randomBytes } from '@aztec/foundation/crypto';
12+
import {
13+
AccountFeePaymentMethodOptions,
14+
type DefaultAccountEntrypointOptions,
15+
} from '@aztec/entrypoints/account';
16+
import { randomBytes } from '@aztec/foundation/crypto/random';
17+
import { Fr } from '@aztec/foundation/curves/bn254';
1118
import { EcdsaRAccountContract } from '@aztec/accounts/ecdsa/lazy';
1219
import { SchnorrAccountContract } from '@aztec/accounts/schnorr/lazy';
1320

@@ -21,13 +28,11 @@ import {
2128
import {
2229
ExecutionPayload,
2330
mergeExecutionPayloads,
24-
} from '@aztec/entrypoints/payload';
25-
import { TxSimulationResult } from '@aztec/stdlib/tx';
31+
type TxSimulationResult,
32+
} from '@aztec/stdlib/tx';
2633
import { GasSettings } from '@aztec/stdlib/gas';
27-
import {
28-
AccountFeePaymentMethodOptions,
29-
DefaultAccountEntrypointOptions,
30-
} from '@aztec/entrypoints/account';
34+
import { AztecAddress } from '@aztec/stdlib/aztec-address';
35+
import { type FeeOptions, BaseWallet } from '@aztec/wallet-sdk/base-wallet';
3136

3237
const PROVER_ENABLED = false;
3338

@@ -64,20 +69,22 @@ export class EmbeddedWallet extends BaseWallet {
6469
* This wallet will use the sponsoredFPC payment method
6570
* unless otherwise stated
6671
* @param from - The address where the transaction is being sent from
67-
* @param userFeeOptions - User-provided fee options, which might be incomplete
72+
* @param feePayer - The address paying for fees (if embedded in the execution payload)
73+
* @param gasSettings - User-provided partial gas settings
6874
* @returns - Populated fee options that can be used to create a transaction execution request
6975
*/
70-
override async getDefaultFeeOptions(
76+
protected override async completeFeeOptions(
7177
from: AztecAddress,
72-
userFeeOptions: UserFeeOptions | undefined
78+
feePayer?: AztecAddress,
79+
gasSettings?: Partial<GasSettings>
7380
): Promise<FeeOptions> {
7481
const maxFeesPerGas =
75-
userFeeOptions?.gasSettings?.maxFeesPerGas ??
82+
gasSettings?.maxFeesPerGas ??
7683
(await this.aztecNode.getCurrentBaseFees()).mul(1 + this.baseFeePadding);
7784
let walletFeePaymentMethod;
7885
let accountFeePaymentMethodOptions;
7986
// The transaction does not include a fee payment method, so we set a default
80-
if (!userFeeOptions?.embeddedPaymentMethodFeePayer) {
87+
if (!feePayer) {
8188
const sponsoredFPCContract =
8289
await EmbeddedWallet.#getSponsoredPFCContract();
8390
walletFeePaymentMethod = new SponsoredFeePaymentMethod(
@@ -87,19 +94,17 @@ export class EmbeddedWallet extends BaseWallet {
8794
} else {
8895
// The transaction includes fee payment method, so we check if we are the fee payer for it
8996
// (this can only happen if the embedded payment method is FeeJuiceWithClaim)
90-
accountFeePaymentMethodOptions = from.equals(
91-
userFeeOptions.embeddedPaymentMethodFeePayer
92-
)
97+
accountFeePaymentMethodOptions = from.equals(feePayer)
9398
? AccountFeePaymentMethodOptions.FEE_JUICE_WITH_CLAIM
9499
: AccountFeePaymentMethodOptions.EXTERNAL;
95100
}
96-
const gasSettings: GasSettings = GasSettings.default({
97-
...userFeeOptions?.gasSettings,
101+
const fullGasSettings: GasSettings = GasSettings.default({
102+
...gasSettings,
98103
maxFeesPerGas,
99104
});
100-
this.log.debug(`Using L2 gas settings`, gasSettings);
105+
this.log.debug(`Using L2 gas settings`, fullGasSettings);
101106
return {
102-
gasSettings,
107+
gasSettings: fullGasSettings,
103108
walletFeePaymentMethod,
104109
accountFeePaymentMethodOptions,
105110
};
@@ -313,8 +318,16 @@ export class EmbeddedWallet extends BaseWallet {
313318
opts: SimulateOptions
314319
): Promise<TxSimulationResult> {
315320
const feeOptions = opts.fee?.estimateGas
316-
? await this.getFeeOptionsForGasEstimation(opts.from, opts.fee)
317-
: await this.getDefaultFeeOptions(opts.from, opts.fee);
321+
? await this.completeFeeOptionsForEstimation(
322+
opts.from,
323+
executionPayload.feePayer,
324+
opts.fee?.gasSettings
325+
)
326+
: await this.completeFeeOptions(
327+
opts.from,
328+
executionPayload.feePayer,
329+
opts.fee?.gasSettings
330+
);
318331
const feeExecutionPayload =
319332
await feeOptions.walletFeePaymentMethod?.getExecutionPayload();
320333
const executionOptions: DefaultAccountEntrypointOptions = {

app/main.ts

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -100,8 +100,8 @@ createAccountButton.addEventListener('click', async (e) => {
100100
});
101101

102102
// Connect a test account
103-
// Sandbox comes with some test accounts. This can be used instead of creating new ones
104-
// when building against the Sandbox.
103+
// Local network comes with some test accounts. This can be used instead of creating new ones
104+
// when building against the local network.
105105
connectTestAccountButton.addEventListener('click', async (e) => {
106106
e.preventDefault();
107107
const button = e.target as HTMLButtonElement;
@@ -147,7 +147,7 @@ voteButton.addEventListener('click', async (e) => {
147147
}
148148

149149
// Prepare contract interaction
150-
const votingContract = await PrivateVotingContract.at(
150+
const votingContract = PrivateVotingContract.at(
151151
AztecAddress.fromString(contractAddress),
152152
wallet
153153
);
@@ -181,7 +181,7 @@ async function updateVoteTally(wallet: Wallet, from: AztecAddress) {
181181
displayStatusMessage('Updating vote tally...');
182182

183183
// Prepare contract interaction
184-
const votingContract = await PrivateVotingContract.at(
184+
const votingContract = PrivateVotingContract.at(
185185
AztecAddress.fromString(contractAddress),
186186
wallet
187187
);

contracts/Nargo.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,4 +3,4 @@ name = "private_voting"
33
type = "contract"
44

55
[dependencies]
6-
aztec = { git="https://github.com/AztecProtocol/aztec-packages/", tag="v3.0.0-devnet.4", directory="noir-projects/aztec-nr/aztec" }
6+
aztec = { git="https://github.com/AztecProtocol/aztec-packages/", tag="v3.0.0-devnet.20251212", directory="noir-projects/aztec-nr/aztec" }

0 commit comments

Comments
 (0)