Skip to content

Commit

Permalink
Merge pull request #16 from FigureTechnologies/wrouten/sc-216500/upda…
Browse files Browse the repository at this point in the history
…te-capital-denom-v2

Update capital denom and required capital attribute in migration
  • Loading branch information
wrouten-figure authored Mar 17, 2023
2 parents 83c7c40 + 9d01077 commit 6e58634
Show file tree
Hide file tree
Showing 2 changed files with 67 additions and 78 deletions.
140 changes: 63 additions & 77 deletions src/migrate.rs
Original file line number Diff line number Diff line change
@@ -1,13 +1,8 @@
use std::collections::HashSet;
use std::convert::TryInto;
use std::hash::Hash;

use crate::error::ContractError;
use crate::msg::AssetExchange;
use crate::msg::MigrateMsg;
use crate::state::asset_exchange_authorization_storage;
use crate::state::state_storage;
use crate::state::AssetExchangeAuthorization;
use crate::state::State;
use crate::state::CONFIG_KEY;
use crate::version::CONTRACT_NAME;
Expand All @@ -28,65 +23,41 @@ use serde::Serialize;
pub fn migrate(
deps: DepsMut<ProvenanceQuery>,
_: Env,
_: MigrateMsg,
migrate_msg: MigrateMsg,
) -> Result<Response<ProvenanceMsg>, ContractError> {
set_contract_version(deps.storage, CONTRACT_NAME, CONTRACT_VERSION)?;

let old_state: StateV1_0_0 = singleton_read(deps.storage, CONFIG_KEY).load()?;
let old_state: StateV2_0_0 = singleton_read(deps.storage, CONFIG_KEY).load()?;

let capital_denom = match migrate_msg.capital_denom {
None => old_state.capital_denom,
Some(capital_denom) => capital_denom,
};
let new_state = State {
admin: old_state.recovery_admin,
admin: old_state.admin,
lp: old_state.lp,
raise: old_state.raise.clone(),
commitment_denom: format!("{}.commitment", old_state.raise),
investment_denom: format!("{}.investment", old_state.raise),
capital_denom: old_state.capital_denom,
commitment_denom: old_state.commitment_denom,
investment_denom: old_state.investment_denom,
capital_denom,
capital_per_share: old_state.capital_per_share,
required_capital_attribute: None,
required_capital_attribute: migrate_msg.required_capital_attribute,
};

state_storage(deps.storage).save(&new_state)?;

if old_state.status == Status::Draft {
asset_exchange_authorization_storage(deps.storage).save(&vec![
AssetExchangeAuthorization {
exchanges: vec![AssetExchange {
investment: None,
commitment_in_shares: Some(
new_state
.capital_to_shares(old_state.max_commitment)
.try_into()?,
),
capital: None,
date: None,
}],
to: None,
memo: None,
},
])?;
}

Ok(Response::default())
}

#[derive(Serialize, Deserialize, Clone, Debug, PartialEq)]
pub struct StateV1_0_0 {
pub recovery_admin: Addr,
pub struct StateV2_0_0 {
pub admin: Addr,
pub lp: Addr,
pub status: Status,
pub raise: Addr,
pub commitment_denom: String,
pub investment_denom: String,
pub capital_denom: String,
pub capital_per_share: u64,
pub min_commitment: u64,
pub max_commitment: u64,
pub min_days_of_notice: Option<u16>,
pub sequence: u16,
pub active_capital_call: Option<CapitalCall>,
pub closed_capital_calls: HashSet<CapitalCall>,
pub cancelled_capital_calls: HashSet<CapitalCall>,
pub redemptions: HashSet<Redemption>,
pub distributions: HashSet<Distribution>,
pub withdrawals: HashSet<Withdrawal>,
}

#[derive(Serialize, Deserialize, Clone, Debug, PartialEq)]
Expand Down Expand Up @@ -184,71 +155,86 @@ impl Hash for Withdrawal {

#[cfg(test)]
mod tests {
use crate::state::asset_exchange_authorization_storage_read;

use super::*;
use cosmwasm_std::testing::mock_env;
use cosmwasm_storage::singleton;
use provwasm_mocks::mock_dependencies;

use super::StateV1_0_0;
use super::StateV2_0_0;

#[test]
fn migration() {
let mut deps = mock_dependencies(&[]);
singleton(&mut deps.storage, CONFIG_KEY)
.save(&StateV1_0_0 {
recovery_admin: Addr::unchecked("marketpalace"),
status: Status::Draft,
.save(&StateV2_0_0 {
admin: Addr::unchecked("marketpalace"),
lp: Addr::unchecked("lp"),
raise: Addr::unchecked("raise_1"),
commitment_denom: "commitment".to_string(),
investment_denom: "investment".to_string(),
capital_denom: String::from("stable_coin"),
capital_per_share: 100,
min_commitment: 0,
max_commitment: 10_000,
min_days_of_notice: None,
sequence: 0,
active_capital_call: None,
closed_capital_calls: HashSet::new(),
cancelled_capital_calls: HashSet::new(),
redemptions: HashSet::new(),
distributions: HashSet::new(),
withdrawals: HashSet::new(),
})
.unwrap();

migrate(deps.as_mut(), mock_env(), MigrateMsg {}).unwrap();
migrate(
deps.as_mut(),
mock_env(),
MigrateMsg {
capital_denom: None,
required_capital_attribute: None,
},
)
.unwrap();

assert_eq!(
State {
admin: Addr::unchecked("marketpalace"),
lp: Addr::unchecked("lp"),
raise: Addr::unchecked("raise_1"),
commitment_denom: String::from("raise_1.commitment"),
investment_denom: String::from("raise_1.investment"),
commitment_denom: String::from("commitment"),
investment_denom: String::from("investment"),
capital_denom: String::from("stable_coin"),
capital_per_share: 100,
required_capital_attribute: None,
},
singleton_read(&deps.storage, CONFIG_KEY).load().unwrap()
);
}

#[test]
fn migration_with_capital_denom_and_attribute() {
let mut deps = mock_dependencies(&[]);
singleton(&mut deps.storage, CONFIG_KEY)
.save(&StateV2_0_0 {
admin: Addr::unchecked("marketpalace"),
lp: Addr::unchecked("lp"),
raise: Addr::unchecked("raise_1"),
commitment_denom: "commitment".to_string(),
investment_denom: "investment".to_string(),
capital_denom: String::from("stable_coin"),
capital_per_share: 100,
})
.unwrap();

let migration_msg = MigrateMsg {
capital_denom: Some(String::from("new_denom")),
required_capital_attribute: Some(String::from("attr")),
};
migrate(deps.as_mut(), mock_env(), migration_msg).unwrap();

assert_eq!(
&AssetExchangeAuthorization {
exchanges: vec![AssetExchange {
investment: None,
commitment_in_shares: Some(100),
capital: None,
date: None,
}],
to: None,
memo: None,
State {
admin: Addr::unchecked("marketpalace"),
lp: Addr::unchecked("lp"),
raise: Addr::unchecked("raise_1"),
commitment_denom: String::from("commitment"),
investment_denom: String::from("investment"),
capital_denom: String::from("new_denom"),
capital_per_share: 100,
required_capital_attribute: Some(String::from("attr")),
},
asset_exchange_authorization_storage_read(&deps.storage)
.load()
.unwrap()
.get(0)
.unwrap()
singleton_read(&deps.storage, CONFIG_KEY).load().unwrap()
);
}
}
5 changes: 4 additions & 1 deletion src/msg.rs
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,10 @@ pub struct InstantiateMsg {

#[derive(Serialize, Deserialize, Clone, Debug, PartialEq, JsonSchema)]
#[serde(rename_all = "snake_case")]
pub struct MigrateMsg {}
pub struct MigrateMsg {
pub capital_denom: Option<String>,
pub required_capital_attribute: Option<String>,
}

#[derive(Serialize, Deserialize, Clone, Debug, PartialEq, JsonSchema)]
#[serde(rename_all = "snake_case")]
Expand Down

0 comments on commit 6e58634

Please sign in to comment.