В Субстрате есть способ использовать хранилище и функции из одного пользовательского модуля в другом? - PullRequest
5 голосов
/ 05 июля 2019

Я видел Учебное пособие по субстратам по созданию ящиков отдельных модулей времени выполнения субстрата здесь для повторного использования функциональности, но мне было интересно, есть ли способ для одного пользовательского модуля получить доступ к хранилищу илифункции из другого пользовательского модуля?

Что-то в этом роде:

/// In ModuleA

    pub type IndexType = u64;

    decl_storage! {
        trait Store for Module<T: Trait> as ModuleA {
                pub MyIndexCount get(my_index_count): Option<IndexType>;
        }
    }

А затем внутри ModuleB - что мне нужно сделать, чтобы использовать / включить функциональность ModuleA, и как я это называю?

/// In ModuleB

    decl_module! {
    pub struct Module<T: Trait> for enum Call where origin: T::Origin {
        fn deposit_event<T>() = default;

        pub fn edit_index(origin) -> Result {
            let sender = ensure_signed(origin)?;

            // --->>>> I want to read some storage from ModuleA whilst inside ModuleB
            let c: IndexType = ReadStorageFromModuleA >>> my_index_count().ok_or("Storage Read Error: cannot get index")?;

            // change storage in ModuleA from ModuleB
            WriteToStorageInModuleA <MyIndexCount<T>>::put(&c + 1);

            Ok(())
            }
        }
    }    

1 Ответ

4 голосов
/ 10 июля 2019

Если вы создаете модуль (module2), который напрямую зависит от другого модуля (module1), вы должны унаследовать свойство module1 в определении свойства module2:

pub trait Trait: module1::Trait {
    ...
}

Для доступа к public элементы хранения из module1 в module2, вам нужно сделать следующее:

  • Импортировать соответствующую черту хранения для доступа к API хранения: StorageValue, StorageMap и т. Д. *
  • Доступ к общедоступному хранилищу через тип хранилища module1
    • <module1::Something<T>>::get()
    • <module1::Something<T>>::put()
    • и т. Д. *

Для доступа к другим общедоступным функциям из модуля 1 в модуле 2 необходимо использовать тип Module:

<module1::Module<T>>::public_function();

Вот простой пример двух модулейвзаимодействуя следующим образом:

module1.rs

Обратите внимание, что все элементы в этом модуле помечены как общедоступные (pub)

use support::{decl_module, decl_storage, StorageValue};

pub trait Trait: system::Trait {}

decl_storage! {
    trait Store for Module<T: Trait> as TemplateModule {
        pub Something: u32;
    }
}

decl_module! {
    pub struct Module<T: Trait> for enum Call where origin: T::Origin {
    }
}

impl<T: Trait> Module<T> {
    pub fn get_value() -> u32 {
        <Something<T>>::get()
    }
}

module2.rs

use support::{decl_module, decl_event, StorageValue, dispatch::Result};
use system::ensure_signed;

use crate::module1;

pub trait Trait: module1::Trait {
    type Event: From<Event<Self>> + Into<<Self as system::Trait>::Event>;
}

decl_module! {
    /// The module declaration.
    pub struct Module<T: Trait> for enum Call where origin: T::Origin {
        fn deposit_event<T>() = default;

        pub fn get_value_directly(origin) -> Result {
            let who = ensure_signed(origin)?;
            let value = <module1::Something<T>>::get();
            Self::deposit_event(RawEvent::ValueIs(value, who));
            Ok(())
        }

        pub fn set_value_directly(origin, value: u32) -> Result {
            let _ = ensure_signed(origin)?;
            <module1::Something<T>>::put(value);
            Ok(())
        }

        pub fn get_value_public_function(origin) -> Result {
            let who = ensure_signed(origin)?;
            let value = <module1::Module<T>>::get_value();
            Self::deposit_event(RawEvent::ValueIs(value, who));
            Ok(())
        }
    }
}

decl_event!(
    pub enum Event<T> where <T as system::Trait>::AccountId {
        ValueIs(u32, AccountId),
    }
);
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...