Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
24 commits
Select commit Hold shift + click to select a range
4099ddd
chore(vetkeys): migrate basic_timelock_ibe to icp-cli and @icp-sdk/ve…
marc0olo May 29, 2026
1114357
fix(ci): update basic_timelock_ibe to ic-cdk 0.20.1 and @icp-sdk/auth…
marc0olo May 30, 2026
08d0cb4
fix(basic_timelock_ibe): resolve gen_bindings.sh path issue
marc0olo Jun 1, 2026
451a6d1
fix(basic_timelock_ibe): bump ic-cdk-timers and ic-stable-structures
marc0olo Jun 1, 2026
8e25c73
fix(basic_timelock_ibe): ic-cdk-timers 1.0.0 (0.13.x does not exist)
marc0olo Jun 1, 2026
dea944a
fix(basic_timelock_ibe): revert ic-stable-structures to 0.6.8
marc0olo Jun 1, 2026
9fdba5e
chore(basic_timelock_ibe): rename CI job keys to remove rust-vetkeys-…
marc0olo Jun 1, 2026
cc5e815
chore(basic_timelock_ibe): rename CI jobs to language-first format
marc0olo Jun 1, 2026
ac6e0a5
fix(basic_timelock_ibe): update set_timer_interval for ic-cdk-timers …
marc0olo Jun 1, 2026
9271cd2
fix(basic_timelock_ibe): fix declaration imports in main.ts
marc0olo Jun 1, 2026
66160be
fix: use key_1 (not test_key_1), npx --yes, console.error in basic_ibe
marc0olo Jun 1, 2026
a6dfad0
docs: update vetkeys doc links to docs.internetcomputer.org/concepts/…
marc0olo Jun 1, 2026
165e020
refactor: use generated createActor and Backend type from declarations
marc0olo Jun 1, 2026
77959a5
docs: add folder structure, fix dev command and cd instructions
marc0olo Jun 1, 2026
8dea49b
fix: simplify rootKey; use /authorize (not /#authorize) and https://i…
marc0olo Jun 2, 2026
e931953
fix: use https://id.ai/authorize for production identityProvider
marc0olo Jun 2, 2026
f9dbdaa
fix: switch back to test_key_1 (supported again in latest icp-cli-net…
marc0olo Jun 3, 2026
d1b5742
ci: switch to icp-dev-env container images, Ubuntu only
marc0olo Jun 3, 2026
4869899
ci: rename workflow files to vetkeys-{example}.yml convention
marc0olo Jun 3, 2026
73f223b
ci: fix workflow name and simplify job IDs to rust/motoko only
marc0olo Jun 3, 2026
f59b037
ci: pass ICP_CLI_GITHUB_TOKEN to avoid network launcher rate limiting
marc0olo Jun 3, 2026
ba29c2d
fix: use LocalStorage to avoid IDBDatabase race condition on dev server
marc0olo Jun 3, 2026
e4c19ac
fix: use LocalStorage only on localhost as workaround for IDB race co…
marc0olo Jun 3, 2026
411749a
fix(basic_timelock_ibe): make npm run dev work directly
marc0olo Jun 3, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
26 changes: 26 additions & 0 deletions .github/workflows/vetkeys-basic-timelock-ibe.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
name: vetkeys-basic-timelock-ibe

on:
push:
branches:
- master
pull_request:
paths:
- rust/vetkeys/basic_timelock_ibe/**
- .github/workflows/vetkeys-basic-timelock-ibe.yml

concurrency:
group: ${{ github.workflow }}-${{ github.ref }}
cancel-in-progress: true

jobs:
rust:
runs-on: ubuntu-24.04
container: ghcr.io/dfinity/icp-dev-env-rust:0.1.0
env:
ICP_CLI_GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
steps:
- uses: actions/checkout@34e114876b0b11c390a56381ad16ebd13914f8d5 # v4.3.1
- name: Deploy Basic Timelock Ibe Rust
working-directory: rust/vetkeys/basic_timelock_ibe
run: icp network start -d && icp deploy
40 changes: 29 additions & 11 deletions rust/vetkeys/basic_timelock_ibe/README.md
Original file line number Diff line number Diff line change
@@ -1,8 +1,10 @@
# Timelock Encryption

<!-- TODO: re-enable once icp.ninja supports icp-cli (currently requires dfx)
[![](https://icp.ninja/assets/open.svg)](http://icp.ninja/editor?g=https://github.com/dfinity/examples/tree/master/rust/vetkeys/basic_timelock_ibe)
-->

The **Basic Timelock IBE** example demonstrates how to use **[VetKeys](https://internetcomputer.org/docs/building-apps/network-features/vetkeys/introduction)** to implement a secret-bid auction using timelock encryption on the **Internet Computer (IC)**. This application allows users authenticated with their **Internet Identity Principal** to create auction lots with a description and deadline, and other users to place a secret bid for the lot. The bids in this example are just dummy integer values, contrary to real-world use cases where users would place bids holding some value.
The **Basic Timelock IBE** example demonstrates how to use **[VetKeys](https://docs.internetcomputer.org/concepts/vetkeys)** to implement a secret-bid auction using timelock encryption on the **Internet Computer (IC)**. This application allows users authenticated with their **Internet Identity Principal** to create auction lots with a description and deadline, and other users to place a secret bid for the lot. The bids in this example are just dummy integer values, contrary to real-world use cases where users would place bids holding some value.

This canister (IC smart contract) ensures that:
1. Only authorized users can create auction lots and place secret bids until the lot is closed.
Expand Down Expand Up @@ -31,17 +33,39 @@ A canister functionality for decrypting secrets can be detected by inspecting th

### Prerequisites

- [Internet Computer software development kit](https://internetcomputer.org/docs/building-apps/getting-started/install)
- [ICP CLI](https://cli.internetcomputer.org)
- [npm](https://www.npmjs.com/package/npm)

### (Optionally) Choose a Different Master Key

This example uses `test_key_1` by default. To use a different [available master key](https://internetcomputer.org/docs/building-apps/network-features/vetkeys/api#available-master-keys), change the `"init_arg": "(\"test_key_1\")"` line in `dfx.json` to the desired key before running `dfx deploy` in the next step.
This example uses `test_key_1` by default. To use a different [available master key](https://docs.internetcomputer.org/concepts/vetkeys/#api-overview), change the `init_args` value in `icp.yaml` to the desired key before running `icp deploy` in the next step.

### Folder Structure

This example has a single **Rust** backend with `icp.yaml` at the example root:

```
basic_timelock_ibe/
├── frontend/ ← frontend
├── backend/ ← Rust canister source
└── icp.yaml ← deployment config
```

### Deploy the Canisters Locally

```bash
dfx start --background && dfx deploy
icp network start -d && icp deploy
```

To run the frontend in development mode with hot reloading (after running `icp deploy`):
```bash
cd frontend
npm run dev:rust
```

When you are done testing, stop the local network to free up resources and unblock the default port for other projects:
```bash
icp network stop
```

## Example Components
Expand All @@ -61,13 +85,7 @@ The frontend is a vanilla typescript application providing a simple interface fo
* Viewing open and closed lots including winners and bidders
* Placing a secret bid for open lots created by other users

To run the frontend in development mode with hot reloading (after running `dfx deploy`):

```bash
npm run dev
```

## Additional Resources

- **[Basic IBE Example](../basic_ibe/)** - If you are interested in using IBE with users decrypting secrets.
- **[What are VetKeys](https://internetcomputer.org/docs/building-apps/network-features/vetkeys/introduction)** - For more information about VetKeys and VetKD.
- **[What are VetKeys](https://docs.internetcomputer.org/concepts/vetkeys)** - For more information about VetKeys and VetKD.
7 changes: 4 additions & 3 deletions rust/vetkeys/basic_timelock_ibe/backend/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -15,11 +15,12 @@ crate-type = ["cdylib"]
[dependencies]
candid = "0.10.2"
getrandom = { version = "0.2", features = ["custom"]}
ic-cdk = "0.18.3"
ic-cdk-timers = "0.12.0"
ic-cdk = "0.20.1"
ic-cdk-management-canister = "0.1.1"
ic-cdk-timers = "1.0.0"
ic-dummy-getrandom-for-wasm = "0.1.0"
ic-stable-structures = "0.6.8"
ic-vetkeys = "0.3.0"
ic-vetkeys = "0.7.0"
serde = "1.0.217"
serde_bytes = "0.11.15"
serde_cbor = "0.11.2"
Expand Down
2 changes: 1 addition & 1 deletion rust/vetkeys/basic_timelock_ibe/backend/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -12,4 +12,4 @@ extract-candid: compile-wasm
.SILENT: clean
clean:
cargo clean
rm -rf ../.dfx
rm -rf ../.icp
9 changes: 8 additions & 1 deletion rust/vetkeys/basic_timelock_ibe/backend/backend.did
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,14 @@ type LotInformation = record {
end_time : nat64;
start_time : nat64;
};
type LotStatus = variant { Open; ClosedWithWinner : principal; ClosedNoBids };
type LotStatus = variant {
// The auction is still open
Open;
// The auction is closed and the winner is the principal in the tuple
ClosedWithWinner : principal;
// The auction is closed and no bids were made
ClosedNoBids;
};
type OpenLotsResponse = record {
lots : vec LotInformation;
bidders : vec vec principal;
Expand Down
10 changes: 4 additions & 6 deletions rust/vetkeys/basic_timelock_ibe/backend/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ use crate::types::{
BidCounter, DecryptedBid, EncryptedBid, LotId, LotInformation, VetKeyPublicKey,
};
use candid::Principal;
use ic_cdk::management_canister::{VetKDCurve, VetKDDeriveKeyArgs, VetKDKeyId, VetKDPublicKeyArgs};
use ic_cdk_management_canister::{VetKDCurve, VetKDDeriveKeyArgs, VetKDKeyId, VetKDPublicKeyArgs};
use ic_cdk::{init, post_upgrade, query, update};
use ic_stable_structures::memory_manager::{MemoryId, MemoryManager, VirtualMemory};
use ic_stable_structures::{BTreeMap as StableBTreeMap, Cell as StableCell, DefaultMemoryImpl};
Expand Down Expand Up @@ -109,7 +109,7 @@ async fn get_ibe_public_key() -> VetKeyPublicKey {
key_id: key_id(),
};

let result = ic_cdk::management_canister::vetkd_public_key(&request)
let result = ic_cdk_management_canister::vetkd_public_key(&request)
.await
.expect("call to vetkd_public_key failed");

Expand Down Expand Up @@ -213,9 +213,7 @@ fn place_bid(lot_id: u128, encrypted_amount: Vec<u8>) -> Result<(), String> {
#[update(guard = "is_self_call")]
fn start_lot_closing_timer_job_with_interval_secs(secs: u64) {
let secs = std::time::Duration::from_secs(secs);
ic_cdk_timers::set_timer_interval(secs, || {
ic_cdk::futures::spawn(close_one_lot_if_any_is_open_and_expired())
});
ic_cdk_timers::set_timer_interval(secs, || close_one_lot_if_any_is_open_and_expired());
}

async fn close_one_lot_if_any_is_open_and_expired() {
Expand Down Expand Up @@ -272,7 +270,7 @@ async fn decrypt_ciphertexts(
transport_public_key: transport_secret_key.public_key().to_vec(),
};

let result = ic_cdk::management_canister::vetkd_derive_key(&request)
let result = ic_cdk_management_canister::vetkd_derive_key(&request)
.await
.expect("call to vetkd_derive_key failed");

Expand Down
43 changes: 0 additions & 43 deletions rust/vetkeys/basic_timelock_ibe/dfx.json

This file was deleted.

13 changes: 6 additions & 7 deletions rust/vetkeys/basic_timelock_ibe/frontend/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,8 @@
"version": "0.0.0",
"type": "module",
"scripts": {
"dev": "npm run build:bindings && vite",
"dev": "npm run dev:rust",
"dev:rust": "npm run build:bindings && BACKEND=. vite",
"build": "npm run build:bindings && tsc && vite build",
"build:bindings": "cd scripts && ./gen_bindings.sh",
"preview": "vite preview",
Expand All @@ -20,13 +21,11 @@
"tslib": "^2.8.1",
"typescript": "~5.7.2",
"typescript-eslint": "^8.35.0",
"vite": "^6.4.1",
"vite-plugin-environment": "^1.1.3"
"vite": "^6.4.1"
},
"dependencies": {
"@dfinity/agent": "^2.4.1",
"@dfinity/auth-client": "^2.4.1",
"@dfinity/principal": "^2.4.1",
"@dfinity/vetkeys": "^0.3.0"
"@icp-sdk/auth": "^7.1.0",
"@icp-sdk/core": "^5.4.0",
"@icp-sdk/vetkeys": "^0.5.0-beta.0"
}
}
Original file line number Diff line number Diff line change
@@ -1,8 +1,19 @@
#!/bin/bash
set -eu

cd ../../backend && make extract-candid && dfx generate basic_timelock_ibe && cd ../frontend && rm -r ./src/declarations >> /dev/null 2>&1
mv ../src/declarations ./src && rmdir ../src
# Resolve the script's physical location so we work correctly even when
# frontend/ is reached via a symlink.
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd -P)"
FRONTEND_DIR="$(dirname "$SCRIPT_DIR")"
EXAMPLE_ROOT="$(dirname "$FRONTEND_DIR")"

# dfx 0.31+ generates @icp-sdk/core imports; rewrite to @dfinity/* to match deps
find ./src/declarations -type f \( -name '*.ts' -o -name '*.js' \) -exec \
perl -i -pe 's|\@icp-sdk/core/agent|\@dfinity/agent|g; s|\@icp-sdk/core/principal|\@dfinity/principal|g; s|\@icp-sdk/core/candid|\@dfinity/candid|g' {} +
if command -v candid-extractor >/dev/null 2>&1; then
(cd "$EXAMPLE_ROOT/backend" && make extract-candid)
fi

rm -rf "$FRONTEND_DIR/src/declarations/basic_timelock_ibe"
mkdir -p "$FRONTEND_DIR/src/declarations/basic_timelock_ibe"
npx --yes @icp-sdk/bindgen \
--did-file "$EXAMPLE_ROOT/backend/backend.did" \
--out-dir "$FRONTEND_DIR/src/declarations/basic_timelock_ibe" \
--declarations-flat --force
Loading
Loading