Skip to content

Commit 1e9772a

Browse files
authored
Merge pull request icon-project#371 from icon-project/feat/configure-upgrade-authority
chore: configure upgrade authority
2 parents 807bd92 + 4d21d6c commit 1e9772a

File tree

12 files changed

+136
-2
lines changed

12 files changed

+136
-2
lines changed

contracts/soroban/contracts/centralized-connection/src/contract.rs

+14-1
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@ impl CentralizedConnection {
1414
storage::store_conn_sn(&env, 0);
1515
storage::store_admin(&env, msg.relayer);
1616
storage::store_xcall(&env, msg.xcall_address);
17+
storage::store_upgrade_authority(&env, msg.upgrade_authority);
1718

1819
Ok(())
1920
}
@@ -29,6 +30,18 @@ impl CentralizedConnection {
2930
Ok(())
3031
}
3132

33+
pub fn get_upgrade_authority(env: Env) -> Result<Address, ContractError> {
34+
let address = storage::get_upgrade_authority(&env)?;
35+
Ok(address)
36+
}
37+
38+
pub fn set_upgrade_authority(env: &Env, address: Address) -> Result<(), ContractError> {
39+
helpers::ensure_upgrade_authority(&env)?;
40+
storage::store_upgrade_authority(&env, address);
41+
42+
Ok(())
43+
}
44+
3245
pub fn send_message(
3346
env: Env,
3447
tx_origin: Address,
@@ -109,7 +122,7 @@ impl CentralizedConnection {
109122
}
110123

111124
pub fn upgrade(env: Env, new_wasm_hash: BytesN<32>) -> Result<(), ContractError> {
112-
helpers::ensure_admin(&env)?;
125+
helpers::ensure_upgrade_authority(&env)?;
113126
env.deployer().update_current_contract_wasm(new_wasm_hash);
114127

115128
Ok(())

contracts/soroban/contracts/centralized-connection/src/helpers.rs

+7
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,13 @@ pub fn ensure_admin(e: &Env) -> Result<Address, ContractError> {
99
Ok(admin)
1010
}
1111

12+
pub fn ensure_upgrade_authority(e: &Env) -> Result<Address, ContractError> {
13+
let authority = storage::get_upgrade_authority(&e)?;
14+
authority.require_auth();
15+
16+
Ok(authority)
17+
}
18+
1219
pub fn ensure_xcall(e: &Env) -> Result<Address, ContractError> {
1320
let xcall = storage::get_xcall(&e)?;
1421
xcall.require_auth();

contracts/soroban/contracts/centralized-connection/src/storage.rs

+13
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,13 @@ pub fn admin(e: &Env) -> Result<Address, ContractError> {
2929
.ok_or(ContractError::Uninitialized)
3030
}
3131

32+
pub fn get_upgrade_authority(e: &Env) -> Result<Address, ContractError> {
33+
e.storage()
34+
.instance()
35+
.get(&StorageKey::UpgradeAuthority)
36+
.ok_or(ContractError::Uninitialized)
37+
}
38+
3239
pub fn get_xcall(e: &Env) -> Result<Address, ContractError> {
3340
e.storage()
3441
.instance()
@@ -106,6 +113,12 @@ pub fn store_admin(e: &Env, admin: Address) {
106113
e.storage().instance().set(&StorageKey::Admin, &admin);
107114
}
108115

116+
pub fn store_upgrade_authority(e: &Env, address: Address) {
117+
e.storage()
118+
.instance()
119+
.set(&StorageKey::UpgradeAuthority, &address);
120+
}
121+
109122
pub fn store_xcall(e: &Env, xcall: Address) {
110123
e.storage().instance().set(&StorageKey::Xcall, &xcall);
111124
}

contracts/soroban/contracts/centralized-connection/src/test.rs

+32
Original file line numberDiff line numberDiff line change
@@ -26,6 +26,7 @@ pub struct TestContext {
2626
native_token: Address,
2727
token_admin: Address,
2828
nid: String,
29+
upgrade_authority: Address,
2930
}
3031

3132
impl TestContext {
@@ -38,6 +39,7 @@ impl TestContext {
3839
relayer: Address::generate(&env),
3940
native_token: env.register_stellar_asset_contract(token_admin.clone()),
4041
nid: String::from_str(&env, "icon"),
42+
upgrade_authority: Address::generate(&env),
4143
env,
4244
token_admin,
4345
}
@@ -50,6 +52,7 @@ impl TestContext {
5052
relayer: self.relayer.clone(),
5153
native_token: self.native_token.clone(),
5254
xcall_address: self.xcall.clone(),
55+
upgrade_authority: self.upgrade_authority.clone(),
5356
});
5457
}
5558

@@ -66,6 +69,7 @@ fn get_dummy_initialize_msg(env: &Env) -> InitializeMsg {
6669
relayer: Address::generate(&env),
6770
native_token: env.register_stellar_asset_contract(Address::generate(&env)),
6871
xcall_address: Address::generate(&env),
72+
upgrade_authority: Address::generate(&env),
6973
}
7074
}
7175

@@ -143,6 +147,34 @@ fn test_set_admin_fail() {
143147
)
144148
}
145149

150+
#[test]
151+
fn test_set_upgrade_authority() {
152+
let ctx = TestContext::default();
153+
let client = CentralizedConnectionClient::new(&ctx.env, &ctx.contract);
154+
ctx.init_context(&client);
155+
156+
let new_upgrade_authority = Address::generate(&ctx.env);
157+
client.set_upgrade_authority(&new_upgrade_authority);
158+
159+
assert_eq!(
160+
ctx.env.auths(),
161+
std::vec![(
162+
ctx.upgrade_authority.clone(),
163+
AuthorizedInvocation {
164+
function: AuthorizedFunction::Contract((
165+
ctx.contract.clone(),
166+
Symbol::new(&ctx.env, "set_upgrade_authority"),
167+
(&new_upgrade_authority,).into_val(&ctx.env)
168+
)),
169+
sub_invocations: std::vec![]
170+
}
171+
)]
172+
);
173+
174+
let autorhity = client.get_upgrade_authority();
175+
assert_eq!(autorhity, new_upgrade_authority);
176+
}
177+
146178
#[test]
147179
fn test_set_fee() {
148180
let ctx = TestContext::default();

contracts/soroban/contracts/centralized-connection/src/types.rs

+2
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ use soroban_sdk::{contracttype, Address, String};
55
pub enum StorageKey {
66
Xcall,
77
Admin,
8+
UpgradeAuthority,
89
Xlm,
910
ConnSn,
1011
NetworkFee(String),
@@ -16,6 +17,7 @@ pub struct InitializeMsg {
1617
pub relayer: Address,
1718
pub native_token: Address,
1819
pub xcall_address: Address,
20+
pub upgrade_authority: Address,
1921
}
2022

2123
#[contracttype]

contracts/soroban/contracts/xcall/src/contract.rs

+14-1
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ impl Xcall {
1717

1818
storage::store_admin(&env, &msg.sender);
1919
storage::store_fee_handler(&env, &msg.sender);
20+
storage::store_upgrade_authority(&env, &msg.upgrade_authority);
2021
storage::store_config(
2122
&env,
2223
Config {
@@ -35,6 +36,13 @@ impl Xcall {
3536
Ok(())
3637
}
3738

39+
pub fn set_upgrade_authority(env: &Env, address: Address) -> Result<(), ContractError> {
40+
helpers::ensure_upgrade_authority(&env)?;
41+
storage::store_upgrade_authority(&env, &address);
42+
43+
Ok(())
44+
}
45+
3846
pub fn set_protocol_fee(env: &Env, fee: u128) -> Result<(), ContractError> {
3947
helpers::ensure_admin(&env)?;
4048
storage::store_protocol_fee(&env, fee);
@@ -101,6 +109,11 @@ impl Xcall {
101109
Ok(admin)
102110
}
103111

112+
pub fn get_upgrade_authority(env: Env) -> Result<Address, ContractError> {
113+
let address = storage::get_upgrade_authority(&env)?;
114+
Ok(address)
115+
}
116+
104117
pub fn get_network_address(env: Env) -> Result<String, ContractError> {
105118
let network_address = storage::get_own_network_address(&env)?;
106119
Ok(network_address.to_string())
@@ -137,7 +150,7 @@ impl Xcall {
137150
}
138151

139152
pub fn upgrade(env: Env, new_wasm_hash: BytesN<32>) -> Result<(), ContractError> {
140-
helpers::ensure_admin(&env)?;
153+
helpers::ensure_upgrade_authority(&env)?;
141154
env.deployer().update_current_contract_wasm(new_wasm_hash);
142155

143156
Ok(())

contracts/soroban/contracts/xcall/src/helpers.rs

+7
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,13 @@ pub fn ensure_admin(e: &Env) -> Result<Address, ContractError> {
1717
Ok(admin)
1818
}
1919

20+
pub fn ensure_upgrade_authority(e: &Env) -> Result<Address, ContractError> {
21+
let authority = storage::get_upgrade_authority(&e)?;
22+
authority.require_auth();
23+
24+
Ok(authority)
25+
}
26+
2027
pub fn ensure_fee_handler(e: &Env) -> Result<Address, ContractError> {
2128
let fee_handler = storage::get_fee_handler(&e)?;
2229
fee_handler.require_auth();

contracts/soroban/contracts/xcall/src/storage.rs

+14
Original file line numberDiff line numberDiff line change
@@ -54,6 +54,13 @@ pub fn get_fee_handler(e: &Env) -> Result<Address, ContractError> {
5454
.ok_or(ContractError::Uninitialized)
5555
}
5656

57+
pub fn get_upgrade_authority(e: &Env) -> Result<Address, ContractError> {
58+
e.storage()
59+
.instance()
60+
.get(&StorageKey::UpgradeAuthority)
61+
.ok_or(ContractError::Uninitialized)
62+
}
63+
5764
pub fn protocol_fee(e: &Env) -> u128 {
5865
e.storage()
5966
.instance()
@@ -162,6 +169,13 @@ pub fn store_fee_handler(e: &Env, address: &Address) {
162169
extend_instance(e)
163170
}
164171

172+
pub fn store_upgrade_authority(e: &Env, address: &Address) {
173+
e.storage()
174+
.instance()
175+
.set(&StorageKey::UpgradeAuthority, &address);
176+
extend_instance(e)
177+
}
178+
165179
pub fn store_protocol_fee(e: &Env, fee: u128) {
166180
e.storage().instance().set(&StorageKey::ProtocolFee, &fee);
167181
extend_instance(e)

contracts/soroban/contracts/xcall/src/test/contract.rs

+28
Original file line numberDiff line numberDiff line change
@@ -155,3 +155,31 @@ fn test_get_fee() {
155155
let fee = client.get_fee(&ctx.nid, &need_response, &Some(sources));
156156
assert_eq!(fee, protocol_fee + centralized_conn_fee)
157157
}
158+
159+
#[test]
160+
fn test_set_upgrade_authority() {
161+
let ctx = TestContext::default();
162+
let client = XcallClient::new(&ctx.env, &ctx.contract);
163+
ctx.init_context(&client);
164+
165+
let new_upgrade_authority = Address::generate(&ctx.env);
166+
client.set_upgrade_authority(&new_upgrade_authority);
167+
168+
assert_eq!(
169+
ctx.env.auths(),
170+
std::vec![(
171+
ctx.upgrade_authority.clone(),
172+
AuthorizedInvocation {
173+
function: AuthorizedFunction::Contract((
174+
ctx.contract.clone(),
175+
Symbol::new(&ctx.env, "set_upgrade_authority"),
176+
(&new_upgrade_authority,).into_val(&ctx.env)
177+
)),
178+
sub_invocations: std::vec![]
179+
}
180+
)]
181+
);
182+
183+
let autorhity = client.get_upgrade_authority();
184+
assert_eq!(autorhity, new_upgrade_authority);
185+
}

contracts/soroban/contracts/xcall/src/test/setup.rs

+3
Original file line numberDiff line numberDiff line change
@@ -114,6 +114,7 @@ pub struct TestContext {
114114
pub native_token: Address,
115115
pub token_admin: Address,
116116
pub network_address: NetworkAddress,
117+
pub upgrade_authority: Address,
117118
pub centralized_connection: Address,
118119
}
119120

@@ -130,6 +131,7 @@ impl TestContext {
130131
native_token: env.register_stellar_asset_contract(token_admin.clone()),
131132
nid: String::from_str(&env, "stellar"),
132133
network_address: get_dummy_network_address(&env),
134+
upgrade_authority: Address::generate(&env),
133135
env,
134136
token_admin,
135137
centralized_connection,
@@ -143,6 +145,7 @@ impl TestContext {
143145
sender: self.admin.clone(),
144146
network_id: String::from_str(&self.env, "icon"),
145147
native_token: self.native_token.clone(),
148+
upgrade_authority: self.upgrade_authority.clone(),
146149
});
147150

148151
self.init_connection_state();

contracts/soroban/contracts/xcall/src/types/message.rs

+1
Original file line numberDiff line numberDiff line change
@@ -91,4 +91,5 @@ pub struct InitializeMsg {
9191
pub network_id: String,
9292
pub sender: Address,
9393
pub native_token: Address,
94+
pub upgrade_authority: Address,
9495
}

contracts/soroban/contracts/xcall/src/types/storage_types.rs

+1
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@ pub enum StorageKey {
1414
PendingRequests(BytesN<32>),
1515
PendingResponses(BytesN<32>),
1616
LastReqId,
17+
UpgradeAuthority,
1718
}
1819

1920
#[contracttype]

0 commit comments

Comments
 (0)