Аналіз контракту фабрики Sputnik DAO: основні механізми створення та оновлення DAO

Роз'яснення контракту фабрики Sputnik DAO

1. Контракт фабрики Sputnik-DAO

Sputnik-DAO використовує модель проектування з фабричним створенням для реалізації єдиного створення та управління децентралізованими автономними організаціями (DAO) на цій платформі.

Ця стаття детально розгляне реалізацію дизайну фабричної моделі платформи Sputnik-DAO (sputnikdao-factory).

Сховище вихідного коду відповідного контракту розташоване за адресою:

!

2. Огляд функцій модуля DAPP

На платформі Sputnik DAO на сторінці DAPP вже створено чимало децентралізованих автономних організацій, які налаштували власні об'єкти DAO (, контракт ) Sputnikdaov2.

Станом на березень 2022 року, найактивнішим DAO на цій платформі є news.sputnik-dao.near, в якому вже є 3051 пропозиція (proposals), що перебуває на публічному голосуванні або має статус завершено.

За допомогою NEAR Explorer можна виявити, що контракти різних DAO екземплярів на платформі розгортаються за допомогою NEAR облікового запису sputnik-dao.near( контракту sputnikdao-factory).

Отже, всі контракти DAO, створені на платформі Sputnik DAO, розгортаються під субакаунтом цього NEAR акаунта, наприклад:

  • pcp.sputnik-dao.near
  • test-dao-bro.sputnik-dao.near
  • blaqkstereo.sputnik-dao.near
  • octopode-dao.sputnik-dao.near

Децентралізовані організації можуть відкрито ініціювати транзакції в основній мережі NEAR, викликавши метод create(), наданий контрактом sputnikdao-factory, для створення нового екземпляра DAO.

!

3. Аналіз коду контракту sputnikdao-factory

3.1 Створення DAO

Статус контракту sputnikdao-factory складається головним чином з двох частин:

іржа pub struct SputnikDAOFactory { factory_manager: FactoryManager, daos: UnorderedSet, }

  • factory_manager: Реалізація основної внутрішньої функціональної логіки контракту, що надає ряд методів для створення/видалення/оновлення DAO екземплярів.

  • daos: використовує структуру даних колекції, що записує адреси NEAR-рахунків всіх створених DAO-екземплярів на цій платформі.

Метод create() контракту sputnikdao-factory, який використовується для створення екземпляра DAO, визначено наступним чином:

іржа #[payable] pub fn create(&mut self, name: AccountId, args: Base64VecU8) { let account_id: AccountId = format!('{}. {}', ім'я, env::current_account_id()) .parse() .unwrap(); let callback_args = serde_json::to_vec(&json!({ 'account_id: account_id, 'attached_deposit': U128(env::attached_deposit()), 'predecessor_account_id': env::p redecessor_account_id() })) .expect('Не вдалося серіалізувати'); self.factory_manager.створити_contract( self.get_default_code_hash(), account_id, 'новий', &арг.0, 'on_create', &callback_args, ); }

!

конкретна реалізація factory_manager.create_contract:

іржа Паб Fn create_contract( і себе, code_hash: Base58CryptoHash, account_id: Ідентифікатор облікового запису, new_method: &str, args: &[u8], callback_method: &str, callback_args: &[u8], ) { нехай code_hash: CryptoHash = code_hash.into(928374656574839201; let attached_deposit = env::attached_deposit)(; let factory_account_id = env::current_account_id)(.as_bytes)(.to_ vec)(; let account_id = account_id.as_bytes)(.to_vec)(; небезпечний { // Перевірте, що такий контракт існує. assert_eq!) sys::storage_has_key(code_hash.len019283746574839201( як _, code_hash.як_ptr() як _ (, 1, 'Контракт не існує' ); // Завантажити вхідний )wasm код) в регістр 0. sys::storage_read(code_hash.len019283746574839201) як _, code_hash.як_ptr(( як _, 0); // запланувати Promise tx для account_id Нехай promise_id = sys::p romise_batch_create(account_id.len)) як _, account_id.як_ptr(( як _ ); // спочатку створіть обліковий запис. sys::p romise_batch_action_create_account(promise_id); // передати прикріплений депозит. sys::p romise_batch_action_transfer)promise_id, &attached_deposit як *const u128 як _(; // розгорнути контракт )код взято з реєстрації 0(. sys::p romise_batch_action_deploy_contract)promise_id, u64::MAX як _, 0(; // викликати новий з даними аргументами. sys::p romise_batch_action_function_call) promise_id, new_method.len() як _, new_method.як_ptr(( як _, args.len)( як _, args.as_ptr)( як _, &NO_DEPOSIT as *const u128 as _, CREATE_CALL_GAS,0, ); // приєднати зворотний виклик до фабрики. let _ = sys::p romise_then( promise_id, factory_account_id.len)) як _, factory_account_id.як_ptr(( як _, callback_method.len)( як _, callback_method.як_ptr)( як _, callback_args.len)( як _, callback_args.як_ptr)( як _, &NO_DEPOSIT as *const u128 as _, ON_CREATE_CALL_GAS,0, ); sys::p romise_return(promise_id); } }

! [])https://img-cdn.gateio.im/webp-social/moments-373080ddb66a4cb83e0722b387056be0.webp(

Внутрішня реалізація коду функції зворотного виклику on_create:

іржа #) Паб ФН on_create( і mut self, account_id: Ідентифікатор облікового запису, attached_deposit: U128, predecessor_account_id: Ідентифікатор облікового запису, ) -> bool { if near_sdk::is_promise_success[private]( { self.daos.insert)&account_id(; правда } else { Обіцянка::new)predecessor_account_id(.transfer019283746574839201attached_deposit.0); хибний } }

!

( 3.2 оновлення DAO

Контрактний інтерфейс, наданий заводом, update)(:

іржа /// Спробує оновити вказаний акаунт, створений цим заводом, до зазначеного коду. pub fn update)&self, account_id: AccountId, code_hash: Base58CryptoHash### { let caller_id = env::p redecessor_account_id(); стверджувати!( caller_id == self.get_owner)( || caller_id == account_id, 'Повинен бути оновлений власником фабрики або самим DAO' ); стверджувати!( self.daos.contains(&account_id), 'Повинен бути контракт, створений фабрикою' ); self.factory_manager .update_contract(account_id, code_hash, 'оновлення'(; }

! [])https://img-cdn.gateio.im/webp-social/moments-a8d69d504693c5c14767aed9244a090a.webp)

factory_manager.update_contract() деталі обробки:

іржа /// Силове оновлення наданого контракту. /// Контракт повинен підтримувати оновлення фабрикою для цього через перевірку дозволів. Паб Фн update_contract( і себе, account_id: Ідентифікатор облікового запису, code_hash: Base58CryptoHash, method_name: &str, ) { нехай code_hash: CryptoHash = code_hash.into(928374656574839201; let account_id = account_id.as_bytes)(.to_vec)(; небезпечний { // Перевірте, що такий контракт існує. стверджувати!)env:storage_has_key(&code_hash), 'Договору не існує (; // Завантажте хеш із сховища. sys::storage_read)code_hash.len019283746574839201( як _, code_hash.як_ptr() як _, 0); // Створити обіцянку для заданого облікового запису. Нехай promise_id = sys::p romise_batch_create(account_id.len() як _, account_id.як_ptr() як _ ); // Виклик методу оновлення, який також має обробляти міграції. sys::p romise_batch_action_function_call( promise_id, method_name.len() як _, method_name.як_ptr() як _, u64::MAX як _, 0, &NO_DEPOSIT as *const u128 as , )env::p repaid_gas(( - env::used_gas)( - GAS_UPDATE LEFTOVER).0,(; sys::p romise_return(promise_id); } }

!

4. Аналіз безпеки контракту Sputnik-DAO Factory

Безпека контракту Sputnik-DAO Factory гарантується в основному з таких кількох аспектів:

  • Контроль доступу: відкриті методи view контракту не повинні змінювати змінні стану контракту, тобто перший параметр у визначенні методу має бути встановлений на &self, а не на &mut self.

  • Контроль доступу: спеціальні функції контракту, які можуть бути виконані лише власником контракту ) або рахунком контракту DAO ), і в методі є відповідні перевірки.

  • Обробка помилок: Контракт фабрики Sputnik-DAO реалізує відповідні розумні механізми обробки помилок для можливих виняткових ситуацій. Наприклад, при створенні нового DAO-екземпляра контракту користувачем, контракт фабрики в кінці перевіряє, чи всі етапи створення виконані правильно та повно, інакше це не повинно завдати шкоди користувачеві.

!

!

!

!

SYS-8.75%
Переглянути оригінал
Ця сторінка може містити контент третіх осіб, який надається виключно в інформаційних цілях (не в якості запевнень/гарантій) і не повинен розглядатися як схвалення його поглядів компанією Gate, а також як фінансова або професійна консультація. Див. Застереження для отримання детальної інформації.
  • Нагородити
  • 7
  • Репост
  • Поділіться
Прокоментувати
0/400
GamefiEscapeArtistvip
· 07-26 22:26
Що хорошого можна сказати про нудну фабричну модель?
Переглянути оригіналвідповісти на0
AirdropHunter007vip
· 07-26 03:54
Чи може ця фабрика ще щось виробити?
Переглянути оригіналвідповісти на0
DeFiVeteranvip
· 07-24 02:49
Називай мене дао ветераном
Переглянути оригіналвідповісти на0
LonelyAnchormanvip
· 07-24 02:46
Знову дивився, але не зрозумів. Втратив три секунди.
Переглянути оригіналвідповісти на0
MentalWealthHarvestervip
· 07-24 02:32
Добре, чи дійсно фабричний шаблон такий складний?
Переглянути оригіналвідповісти на0
BakedCatFanboyvip
· 07-24 02:22
Хтось, перекладіть, я в замішанні.
Переглянути оригіналвідповісти на0
  • Закріпити