Skip to content

Commit

Permalink
Add controller storage to account sdk (#800)
Browse files Browse the repository at this point in the history
* Add controller storage to account sdk

* Remove provider generic
  • Loading branch information
tarrencev authored Oct 2, 2024
1 parent 61d2fd0 commit c3315eb
Show file tree
Hide file tree
Showing 17 changed files with 214 additions and 137 deletions.
8 changes: 2 additions & 6 deletions packages/account-wasm/src/account.rs
Original file line number Diff line number Diff line change
@@ -1,5 +1,3 @@
use std::sync::Arc;

use crate::errors::JsControllerError;
use crate::signer::BrowserBackend;
use crate::types::call::JsCall;
Expand All @@ -11,7 +9,6 @@ use crate::types::{Felts, JsFelt};
use account_sdk::artifacts::{Version, CONTROLLERS};
use account_sdk::controller::Controller;
use account_sdk::errors::ControllerError;
use account_sdk::provider::CartridgeJsonRpcProvider;
use serde_wasm_bindgen::to_value;
use starknet::accounts::ConnectedAccount;
use starknet::core::types::Call;
Expand All @@ -25,7 +22,7 @@ type Result<T> = std::result::Result<T, JsError>;

#[wasm_bindgen]
pub struct CartridgeAccount {
controller: Controller<Arc<CartridgeJsonRpcProvider>, BrowserBackend>,
controller: Controller<BrowserBackend>,
}

#[wasm_bindgen]
Expand All @@ -51,15 +48,14 @@ impl CartridgeAccount {
set_panic_hook();

let rpc_url = Url::parse(&rpc_url)?;
let provider = CartridgeJsonRpcProvider::new(rpc_url.clone());

let username = username.to_lowercase();

let controller = Controller::new(
app_id,
username.clone(),
CONTROLLERS[&Version::V1_0_4].hash,
Arc::new(provider),
rpc_url,
signer.try_into()?,
address.0,
chain_id.0,
Expand Down
7 changes: 3 additions & 4 deletions packages/account-wasm/src/session.rs
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,6 @@ use account_sdk::signers::{HashSigner, Signer};
use serde_wasm_bindgen::to_value;
use starknet::accounts::{Account, ConnectedAccount};
use starknet::signers::SigningKey;
use std::sync::Arc;
use url::Url;
use wasm_bindgen::prelude::*;

Expand All @@ -18,7 +17,7 @@ use crate::types::{Felts, JsFelt};
type Result<T> = std::result::Result<T, JsError>;

#[wasm_bindgen]
pub struct CartridgeSessionAccount(SessionAccount<Arc<CartridgeJsonRpcProvider>>);
pub struct CartridgeSessionAccount(SessionAccount);

#[wasm_bindgen]
impl CartridgeSessionAccount {
Expand Down Expand Up @@ -54,7 +53,7 @@ impl CartridgeSessionAccount {
)?;

Ok(CartridgeSessionAccount(SessionAccount::new(
Arc::new(provider),
provider,
signer,
address,
chain_id,
Expand Down Expand Up @@ -91,7 +90,7 @@ impl CartridgeSessionAccount {
)?;

Ok(CartridgeSessionAccount(SessionAccount::new_as_registered(
Arc::new(provider),
provider,
signer,
address,
chain_id,
Expand Down
6 changes: 3 additions & 3 deletions packages/account_sdk/src/account/macros.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
#[macro_export]
macro_rules! impl_execution_encoder {
($type:ident<$($gen:ident : $bound:path),*>) => {
($type:ident $(< $($gen:ident : $bound:path),* >)?) => {
impl<$($gen: $bound + Send),*> ExecutionEncoder for $type<$($gen),*>
{
fn encode_calls(&self, calls: &[Call]) -> Vec<starknet::core::types::Felt> {
Expand All @@ -12,10 +12,10 @@ macro_rules! impl_execution_encoder {

#[macro_export]
macro_rules! impl_account {
($type:ident<$($gen:ident : $bound:path),*>, $is_interactive:expr) => {
($type:ident $(< $($gen:ident : $bound:path),* >)?, $is_interactive:expr) => {
#[cfg_attr(not(target_arch = "wasm32"), async_trait)]
#[cfg_attr(target_arch = "wasm32", async_trait(?Send))]
impl<$($gen: $bound + Send + Sync + Clone),*> Account for $type<$($gen),*>
impl$(<$($gen:$bound + Send + Sync + Clone),*>)* Account for $type$(<$($gen),*>)*
{
type SignError = SignError;

Expand Down
34 changes: 11 additions & 23 deletions packages/account_sdk/src/account/session/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,12 +4,12 @@ use starknet::{
accounts::{Account, ConnectedAccount, ExecutionEncoder},
core::types::{BlockId, BlockTag, Call, Felt},
macros::short_string,
providers::Provider,
};

use crate::{
constants::GUARDIAN_SIGNER,
impl_account, impl_execution_encoder,
provider::CartridgeJsonRpcProvider,
signers::{HashSigner, SignError, Signer},
};

Expand All @@ -24,11 +24,8 @@ pub mod hash;
pub mod merkle;
pub mod raw_session;

pub struct SessionAccount<P>
where
P: Provider + Send,
{
provider: P,
pub struct SessionAccount {
provider: CartridgeJsonRpcProvider,
signer: Signer,
address: Felt,
chain_id: Felt,
Expand All @@ -37,12 +34,9 @@ where
session: Session,
}

impl<P> SessionAccount<P>
where
P: Provider + Send,
{
impl SessionAccount {
pub fn new(
provider: P,
provider: CartridgeJsonRpcProvider,
signer: Signer,
address: Felt,
chain_id: Felt,
Expand All @@ -61,7 +55,7 @@ where
}

pub fn new_as_registered(
provider: P,
provider: CartridgeJsonRpcProvider,
signer: Signer,
address: Felt,
chain_id: Felt,
Expand Down Expand Up @@ -114,10 +108,7 @@ where

#[cfg_attr(not(target_arch = "wasm32"), async_trait)]
#[cfg_attr(target_arch = "wasm32", async_trait(?Send))]
impl<P> AccountHashAndCallsSigner for SessionAccount<P>
where
P: Provider + Send + Sync,
{
impl AccountHashAndCallsSigner for SessionAccount {
async fn sign_hash_and_calls(
&self,
hash: Felt,
Expand All @@ -136,14 +127,11 @@ where
}
}

impl_execution_encoder!(SessionAccount<P: Provider>);
impl_account!(SessionAccount<P: Provider>, |_, _| false);
impl_execution_encoder!(SessionAccount);
impl_account!(SessionAccount, |_, _| false);

impl<P> ConnectedAccount for SessionAccount<P>
where
P: Provider + Send + Sync + Clone,
{
type Provider = P;
impl ConnectedAccount for SessionAccount {
type Provider = CartridgeJsonRpcProvider;

fn provider(&self) -> &Self::Provider {
&self.provider
Expand Down
49 changes: 27 additions & 22 deletions packages/account_sdk/src/controller.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,9 @@ use crate::account::{AccountHashAndCallsSigner, CallEncoder};
use crate::constants::{ETH_CONTRACT_ADDRESS, WEBAUTHN_GAS};
use crate::errors::ControllerError;
use crate::factory::ControllerFactory;
use crate::provider::CartridgeProvider;
use crate::provider::CartridgeJsonRpcProvider;
use crate::signers::Signer;
use crate::storage::StorageValue;
use crate::storage::ControllerMetadata;
use crate::typed_data::TypedData;
use crate::{
abigen::{self},
Expand All @@ -21,51 +21,53 @@ use starknet::core::types::{
};
use starknet::core::utils::cairo_short_string_to_felt;
use starknet::macros::selector;
use starknet::providers::ProviderError;
use starknet::providers::{Provider, ProviderError};
use starknet::signers::SignerInteractivityContext;
use starknet::{
accounts::{Account, ConnectedAccount, ExecutionEncoder},
core::types::{BlockId, Felt},
};
use url::Url;

#[cfg(test)]
#[path = "controller_test.rs"]
mod controller_test;

#[derive(Clone)]
pub struct Controller<P, B>
pub struct Controller<B>
where
P: CartridgeProvider + Send + Sync + Clone,
B: Backend + Clone,
{
pub(crate) app_id: String,
pub(crate) address: Felt,
pub(crate) chain_id: Felt,
pub(crate) class_hash: Felt,
pub(crate) rpc_url: Url,
pub username: String,
salt: Felt,
provider: P,
pub(crate) salt: Felt,
provider: CartridgeJsonRpcProvider,
pub(crate) owner: Signer,
contract: Option<Box<abigen::controller::Controller<Self>>>,
pub factory: ControllerFactory<P>,
pub factory: ControllerFactory,
pub(crate) backend: B,
}

impl<P, B> Controller<P, B>
impl<B> Controller<B>
where
P: CartridgeProvider + Send + Sync + Clone,
B: Backend + Clone,
{
#[allow(clippy::too_many_arguments)]
pub fn new(
app_id: String,
username: String,
class_hash: Felt,
provider: P,
rpc_url: Url,
owner: Signer,
address: Felt,
chain_id: Felt,
backend: B,
) -> Self {
let provider = CartridgeJsonRpcProvider::new(rpc_url.clone());
let salt = cairo_short_string_to_felt(&username).unwrap();

let mut calldata = Owner::cairo_serialize(&Owner::Signer(owner.signer()));
Expand All @@ -82,6 +84,8 @@ where
app_id,
address,
chain_id,
class_hash,
rpc_url,
username,
salt,
provider,
Expand All @@ -97,10 +101,15 @@ where
));
controller.contract = Some(contract);

controller
.backend
.set_controller(address, ControllerMetadata::from(&controller))
.expect("Should store controller");

controller
}

pub fn deploy(&self) -> AccountDeploymentV1<'_, ControllerFactory<P>> {
pub fn deploy(&self) -> AccountDeploymentV1<'_, ControllerFactory> {
self.factory.deploy_v1(self.salt)
}

Expand Down Expand Up @@ -193,8 +202,7 @@ where
if !metadata.is_registered {
let mut updated_metadata = metadata;
updated_metadata.is_registered = true;
self.backend
.set(&key, &StorageValue::Session(updated_metadata))?;
self.backend.set_session(&key, updated_metadata)?;
}
}
Ok(tx_result)
Expand Down Expand Up @@ -266,7 +274,7 @@ where
}
}

impl_account!(Controller<P: CartridgeProvider, B: Backend>, |account: &Controller<P, B>, context| {
impl_account!(Controller<B: Backend>, |account: &Controller<B>, context| {
if let SignerInteractivityContext::Execution { calls } = context {
account.session_account(calls).is_none()
} else {
Expand All @@ -276,12 +284,11 @@ impl_account!(Controller<P: CartridgeProvider, B: Backend>, |account: &Controlle

#[cfg_attr(not(target_arch = "wasm32"), async_trait)]
#[cfg_attr(target_arch = "wasm32", async_trait(?Send))]
impl<P, B> ConnectedAccount for Controller<P, B>
impl<B> ConnectedAccount for Controller<B>
where
P: CartridgeProvider + Send + Sync + Clone,
B: Backend + Clone,
{
type Provider = P;
type Provider = CartridgeJsonRpcProvider;

fn provider(&self) -> &Self::Provider {
&self.provider
Expand All @@ -300,9 +307,8 @@ where

#[cfg_attr(not(target_arch = "wasm32"), async_trait)]
#[cfg_attr(target_arch = "wasm32", async_trait(?Send))]
impl<P, B> AccountHashAndCallsSigner for Controller<P, B>
impl<B> AccountHashAndCallsSigner for Controller<B>
where
P: CartridgeProvider + Send + Sync + Clone,
B: Backend + Clone,
{
async fn sign_hash_and_calls(
Expand All @@ -320,9 +326,8 @@ where
}
}

impl<P, B> ExecutionEncoder for Controller<P, B>
impl<B> ExecutionEncoder for Controller<B>
where
P: CartridgeProvider + Send + Sync + Clone,
B: Backend + Clone,
{
fn encode_calls(&self, calls: &[Call]) -> Vec<Felt> {
Expand Down
4 changes: 2 additions & 2 deletions packages/account_sdk/src/controller_test.rs
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@ async fn test_deploy_controller() {
"app_id".to_string(),
username.clone(),
CONTROLLERS[&Version::V1_0_4].hash,
provider.clone(),
runner.rpc_url.clone(),
owner.clone(),
Felt::ZERO,
chain_id,
Expand All @@ -47,7 +47,7 @@ async fn test_deploy_controller() {
"app_id".to_string(),
username.clone(),
CONTROLLERS[&Version::V1_0_4].hash,
provider.clone(),
runner.rpc_url.clone(),
owner.clone(),
address,
chain_id,
Expand Down
3 changes: 1 addition & 2 deletions packages/account_sdk/src/execute_from_outside.rs
Original file line number Diff line number Diff line change
Expand Up @@ -18,9 +18,8 @@ use crate::{
#[path = "execute_from_outside_test.rs"]
mod execute_from_outside_test;

impl<P, B> Controller<P, B>
impl<B> Controller<B>
where
P: CartridgeProvider + Send + Sync + Clone,
B: Backend + Clone,
{
async fn execute_from_outside_raw(
Expand Down
Loading

0 comments on commit c3315eb

Please sign in to comment.