Skip to content

fix: deps deploy works with Canister ID out of the ranges of the pocket-ic subnets #4276

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Open
wants to merge 4 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
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
6 changes: 6 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,12 @@

# UNRELEASED

### fix: deps deploy works with Canister ID out of the ranges of the pocket-ic subnets

The `dfx deps deploy` command didn't work when the pulled dependency's Canister ID is out of the ranges of the `pocket-ic` subnets.

The removed `replica` had one subnet to cover all subnets. While the `pocket-ic` can dynamically create new subnet when trying to create a canister with specified ID.

### chore: update bitcoin regtest configuration to be same as the bitcoin mainnet

Update bitcoin `regtest` configuration to be same as the bitcoin `mainnet`.
Expand Down
4 changes: 2 additions & 2 deletions e2e/assets/deps/onchain/dfx.json
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@
"pullable": {
"wasm_url": "http://httpbin.org/status/404",
"dependencies": [
"yofga-2qaaa-aaaaa-aabsq-cai"
"w36hm-eqaaa-aaaal-qr76a-cai"
],
"init_guide": "No init arguments required"
},
Expand All @@ -33,7 +33,7 @@
"pullable": {
"wasm_url": "http://httpbin.org/status/404",
"dependencies": [
"yofga-2qaaa-aaaaa-aabsq-cai"
"w36hm-eqaaa-aaaal-qr76a-cai"
],
"init_guide": "An optional natural number, e.g. \"(opt 20)\"."
}
Expand Down
40 changes: 11 additions & 29 deletions e2e/tests-dfx/deps.bash
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ teardown() {
standard_teardown
}

CANISTER_ID_A="yofga-2qaaa-aaaaa-aabsq-cai"
CANISTER_ID_A="w36hm-eqaaa-aaaal-qr76a-cai" # This ID is out of the pocket-ic subnets ranges, create it will automatically create a subnet
CANISTER_ID_B="yhgn4-myaaa-aaaaa-aabta-cai"
CANISTER_ID_C="yahli-baaaa-aaaaa-aabtq-cai"

Expand Down Expand Up @@ -47,18 +47,6 @@ setup_onchain() {
cd .. || exit
}

# only execute in project root (deps)
cleanup_onchain() {
cd onchain || exit
dfx canister stop a
dfx canister delete a --no-withdrawal
dfx canister stop b
dfx canister delete b --no-withdrawal
dfx canister stop c
dfx canister delete c --no-withdrawal
cd .. || exit
}

@test "dfx build can write required metadata for pullable" {
dfx_start

Expand Down Expand Up @@ -111,10 +99,7 @@ cleanup_onchain() {
assert_contains "Fetching dependencies of canister $CANISTER_ID_B...
Fetching dependencies of canister $CANISTER_ID_C...
Fetching dependencies of canister $CANISTER_ID_A...
Found 3 dependencies:
$CANISTER_ID_A
$CANISTER_ID_B
$CANISTER_ID_C"
Found 3 dependencies:" # Then canister IDs will be listed, but order doesn't matter
assert_occurs 1 "Fetching dependencies of canister $CANISTER_ID_A..." # common dependency onchain_a is pulled only once
assert_contains "Pulling canister $CANISTER_ID_A...
ERROR: Failed to pull canister $CANISTER_ID_A.
Expand Down Expand Up @@ -432,11 +417,10 @@ candid:args => (nat)"
cd app
assert_command dfx deps pull --network local

# delete onchain canisters so that the replica has no canisters as a clean local replica
cd ../
cleanup_onchain
# start a clean local network which no longer has onchain canisters
dfx stop
dfx_start --clean

cd app
assert_command dfx deps init # b is set here
assert_command dfx deps init "$CANISTER_ID_A" --argument 11
assert_command dfx deps init "$CANISTER_ID_C" --argument "(opt 33)"
Expand Down Expand Up @@ -501,11 +485,10 @@ Installing canister: $CANISTER_ID_C (dep_c)"
cd ../app
assert_command dfx deps pull --network local

# delete onchain canisters so that the replica has no canisters as a clean local replica
cd ../
cleanup_onchain
# start a clean local network which no longer has onchain canisters
dfx stop
dfx_start --clean

cd app
assert_command dfx deps init # b is set here
assert_command dfx deps init "$CANISTER_ID_A" --argument "(opt 11)" # the downloaded wasm need argument type as canister_c
assert_command dfx deps init "$CANISTER_ID_C" --argument "(opt 33)"
Expand Down Expand Up @@ -598,11 +581,10 @@ Installing canister: $CANISTER_ID_C (dep_c)"
cd app
assert_command dfx deps pull --network local

# delete onchain canisters so that the replica has no canisters as a clean local replica
cd ../
cleanup_onchain
# start a clean local network which no longer has onchain canisters
dfx stop
dfx_start --clean

cd app
assert_command_fail dfx canister create dep_b
assert_contains "dep_b is a pull dependency. Please deploy it using \`dfx deps deploy dep_b\`"
assert_command dfx canister create app
Expand Down
25 changes: 14 additions & 11 deletions src/dfx/src/lib/deps/deploy.rs
Original file line number Diff line number Diff line change
Expand Up @@ -17,18 +17,21 @@ pub async fn try_create_canister(
pulled_canister: &PulledCanister,
) -> DfxResult {
let canister_prompt = get_canister_prompt(canister_id, pulled_canister);
match read_state_tree_canister_controllers(agent, *canister_id).await? {
Some(cs) if cs.len() == 1 && cs[0] == Principal::anonymous() => Ok(()),
Some(_) => {
// Check if the canister has been created before.
// If read_state_tree_canister_controllers returns Err, then the pocket-ic doesn't have a subnet covering the canister_id yet.
// We can safely create the canister in this case because the pocket-ic will automatically create the subnet when the canister is created.
if let Ok(Some(cs)) = read_state_tree_canister_controllers(agent, *canister_id).await {
if cs.len() == 1 && cs[0] == Principal::anonymous() {
return Ok(());
} else {
bail!("Canister {canister_id} has been created before and its controller is not the anonymous identity. Please stop and delete it and then deploy again.");
}
None => {
let mgr = ManagementCanister::create(agent);
info!(logger, "Creating canister: {canister_prompt}");
mgr.create_canister()
.as_provisional_create_with_specified_id(*canister_id)
.await?;
Ok(())
}
}

let mgr = ManagementCanister::create(agent);
info!(logger, "Creating canister: {canister_prompt}");
mgr.create_canister()
.as_provisional_create_with_specified_id(*canister_id)
.await?;
Ok(())
}